1/*
2 * Copyright (c) 2002-2004,2011,2014 Apple Inc. All Rights Reserved.
3 *
4 * @APPLE_LICENSE_HEADER_START@
5 *
6 * This file contains Original Code and/or Modifications of Original Code
7 * as defined in and that are subject to the Apple Public Source License
8 * Version 2.0 (the 'License'). You may not use this file except in
9 * compliance with the License. Please obtain a copy of the License at
10 * http://www.opensource.apple.com/apsl/ and read it before using this
11 * file.
12 *
13 * The Original Code and all software distributed under the License are
14 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
15 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
16 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
18 * Please see the License for the specific language governing rights and
19 * limitations under the License.
20 *
21 * @APPLE_LICENSE_HEADER_END@
22 */
23
24/*
25 * simpleprefs.h - plist support for a bare bones Preferences implementation,
26 *                 using only Darwin-avaialble CoreFoundation classes.
27 */
28
29#ifndef _SECURITY_UTILITIES_SIMPLE_PREFS_H_
30#define _SECURITY_UTILITIES_SIMPLE_PREFS_H_
31
32#include <CoreFoundation/CFDictionary.h>
33#include <CoreFoundation/CFString.h>
34#include <security_utilities/utilities.h>
35#include <string>
36
37namespace Security {
38
39/*
40 * PropertyList compatible CFDictionary, nonmutable. All keys are CFStringRefs;
41 * all values are CF objects.
42 */
43class Dictionary
44{
45	NOCOPY(Dictionary)
46
47public:
48
49	/* create from preferences file */
50	typedef enum {
51		US_User,
52		US_System
53	} UserOrSystem;
54
55protected:
56	/* make blank dictionary */
57	Dictionary();
58
59	/* create from arbitrary file */
60	Dictionary(
61		const char		*path);
62
63public:
64	// factory functions for the dictionaries
65	static Dictionary* CreateDictionary(const char* path);
66	static Dictionary* CreateDictionary(const char* domain, UserOrSystem userSys, bool loose = false);
67
68public:
69
70	/* create from existing CFDictionary */
71	Dictionary(
72		CFDictionaryRef	dict);
73
74	virtual ~Dictionary();
75
76	/* basic lookup */
77	const void *getValue(
78		CFStringRef		key);
79
80	/* lookup, value must be CFString (we check) */
81	CFStringRef getStringValue(
82		CFStringRef		key);
83
84	/* lookup, value must be CFData (we check) */
85	CFDataRef getDataValue(
86		CFStringRef		key);
87
88	/* lookup, value must be CFDictionary (we check) */
89	CFDictionaryRef getDictValue(
90		CFStringRef		key);
91
92	/*
93	 * Lookup, value is a dictionary, we return value as Dictionary
94	 * if found, else return NULL.
95	 */
96	Dictionary *copyDictValue(
97		CFStringRef		key);
98
99	/*
100	 * boolean lookup, tolerate many different forms of value.
101	 * Default if value not present is false.
102	 */
103	bool getBoolValue(
104		CFStringRef		key);
105
106	/* basic CF level accessors */
107	CFDictionaryRef		dict()	{ return mDict; }
108	CFIndex				count();
109
110protected:
111	void setDict(
112		CFDictionaryRef	newDict);
113	void initFromFile(
114		const char		*path,
115		bool			loose = false);
116
117	/* this might be a CFMutableDictionary...use accessors for proper typing */
118	CFDictionaryRef		mDict;
119};
120
121/*
122 * PropertyList compatible CFDictionary, mutable.
123 */
124class MutableDictionary : public Dictionary
125{
126	NOCOPY(MutableDictionary)
127public:
128	/* Create an empty mutable dictionary */
129	MutableDictionary();
130
131protected:
132	/* create from arbitrary file */
133	MutableDictionary(
134		const char		*filename);
135
136public:
137
138	static MutableDictionary* CreateMutableDictionary(const char* fileName);
139	static MutableDictionary* CreateMutableDictionary(const char *domain, UserOrSystem userSys);
140
141	/*
142	 * Create from existing CFDictionary (OR CFMutableDictionary).
143	 * I don't see anyway the CF runtime will let us differentiate an
144	 * immutable from a mutable dictionary here, so caller has to tell us.
145	 */
146	MutableDictionary(
147		CFDictionaryRef	dict,
148		bool isMutable);
149
150	virtual ~MutableDictionary();
151
152	/*
153	 * Lookup, value must be CFDictionary (we check). We return a
154	 * mutable copy, or if key not found, we return a new mutable dictionary.
155	 * If you want a NULL return if it's not there, use getDictValue().
156	 */
157	CFMutableDictionaryRef getMutableDictValue(
158		CFStringRef		key);
159
160	/*
161	 * Lookup, value is a dictionary, we return a MutableDictionary, even if
162	 * no value found.
163	 */
164	MutableDictionary *copyMutableDictValue(
165		CFStringRef key);
166
167	/*
168	 * Basic setter. Does a "replace if present, add if not present" op.
169	 */
170	void setValue(
171		CFStringRef		key,
172		CFTypeRef		val);
173
174	/*
175	 * Set key/value pair, data as CFData in the dictionary but passed
176	 * to us as CSSM_DATA.
177	 */
178	void setDataValue(
179		CFStringRef		key,
180		const void *valData,
181		CFIndex valLength);
182
183	/* remove key/value, if present; not an error if it's not */
184	void removeValue(
185		CFStringRef		key);
186
187	/* write as XML property list, both return true on success */
188	bool writePlistToFile(
189		const char		*path);
190
191	/* write XML property list to preferences file */
192	bool writePlistToPrefs(
193		const char		*domain,		// e.g., com.apple.security
194		UserOrSystem	userSys);		// US_User  : ~/Library/Preferences/domain.plist
195										// US_System: /Library/Preferences/domain.plist
196
197	CFMutableDictionaryRef mutableDict()  { return (CFMutableDictionaryRef)dict(); }
198
199private:
200	/* replace mDict with a mutable copy */
201	void makeMutable();
202};
203
204}	/* end namespace Security */
205
206#endif	/* _SECURITY_UTILITIES_SIMPLE_PREFS_H_ */
207