1 //===-- CFCMutableDictionary.cpp ------------------------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #include "CFCMutableDictionary.h"
10 #include "CFCString.h"
11 // CFCString constructor
CFCMutableDictionary(CFMutableDictionaryRef s)12 CFCMutableDictionary::CFCMutableDictionary(CFMutableDictionaryRef s)
13     : CFCReleaser<CFMutableDictionaryRef>(s) {}
14 
15 // CFCMutableDictionary copy constructor
CFCMutableDictionary(const CFCMutableDictionary & rhs)16 CFCMutableDictionary::CFCMutableDictionary(const CFCMutableDictionary &rhs)
17     : CFCReleaser<CFMutableDictionaryRef>(rhs) {}
18 
19 // CFCMutableDictionary copy constructor
20 const CFCMutableDictionary &CFCMutableDictionary::
operator =(const CFCMutableDictionary & rhs)21 operator=(const CFCMutableDictionary &rhs) {
22   if (this != &rhs)
23     *this = rhs;
24   return *this;
25 }
26 
27 // Destructor
~CFCMutableDictionary()28 CFCMutableDictionary::~CFCMutableDictionary() {}
29 
GetCount() const30 CFIndex CFCMutableDictionary::GetCount() const {
31   CFMutableDictionaryRef dict = get();
32   if (dict)
33     return ::CFDictionaryGetCount(dict);
34   return 0;
35 }
36 
GetCountOfKey(const void * key) const37 CFIndex CFCMutableDictionary::GetCountOfKey(const void *key) const
38 
39 {
40   CFMutableDictionaryRef dict = get();
41   if (dict)
42     return ::CFDictionaryGetCountOfKey(dict, key);
43   return 0;
44 }
45 
GetCountOfValue(const void * value) const46 CFIndex CFCMutableDictionary::GetCountOfValue(const void *value) const
47 
48 {
49   CFMutableDictionaryRef dict = get();
50   if (dict)
51     return ::CFDictionaryGetCountOfValue(dict, value);
52   return 0;
53 }
54 
GetKeysAndValues(const void ** keys,const void ** values) const55 void CFCMutableDictionary::GetKeysAndValues(const void **keys,
56                                             const void **values) const {
57   CFMutableDictionaryRef dict = get();
58   if (dict)
59     ::CFDictionaryGetKeysAndValues(dict, keys, values);
60 }
61 
GetValue(const void * key) const62 const void *CFCMutableDictionary::GetValue(const void *key) const
63 
64 {
65   CFMutableDictionaryRef dict = get();
66   if (dict)
67     return ::CFDictionaryGetValue(dict, key);
68   return NULL;
69 }
70 
71 Boolean
GetValueIfPresent(const void * key,const void ** value_handle) const72 CFCMutableDictionary::GetValueIfPresent(const void *key,
73                                         const void **value_handle) const {
74   CFMutableDictionaryRef dict = get();
75   if (dict)
76     return ::CFDictionaryGetValueIfPresent(dict, key, value_handle);
77   return false;
78 }
79 
Dictionary(bool can_create)80 CFMutableDictionaryRef CFCMutableDictionary::Dictionary(bool can_create) {
81   CFMutableDictionaryRef dict = get();
82   if (can_create && dict == NULL) {
83     dict = ::CFDictionaryCreateMutable(kCFAllocatorDefault, 0,
84                                        &kCFTypeDictionaryKeyCallBacks,
85                                        &kCFTypeDictionaryValueCallBacks);
86     reset(dict);
87   }
88   return dict;
89 }
90 
AddValue(CFStringRef key,const void * value,bool can_create)91 bool CFCMutableDictionary::AddValue(CFStringRef key, const void *value,
92                                     bool can_create) {
93   CFMutableDictionaryRef dict = Dictionary(can_create);
94   if (dict != NULL) {
95     // Let the dictionary own the CFNumber
96     ::CFDictionaryAddValue(dict, key, value);
97     return true;
98   }
99   return false;
100 }
101 
SetValue(CFStringRef key,const void * value,bool can_create)102 bool CFCMutableDictionary::SetValue(CFStringRef key, const void *value,
103                                     bool can_create) {
104   CFMutableDictionaryRef dict = Dictionary(can_create);
105   if (dict != NULL) {
106     // Let the dictionary own the CFNumber
107     ::CFDictionarySetValue(dict, key, value);
108     return true;
109   }
110   return false;
111 }
112 
AddValueSInt8(CFStringRef key,int8_t value,bool can_create)113 bool CFCMutableDictionary::AddValueSInt8(CFStringRef key, int8_t value,
114                                          bool can_create) {
115   CFMutableDictionaryRef dict = Dictionary(can_create);
116   if (dict != NULL) {
117     CFCReleaser<CFNumberRef> cf_number(
118         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt8Type, &value));
119     if (cf_number.get()) {
120       // Let the dictionary own the CFNumber
121       ::CFDictionaryAddValue(dict, key, cf_number.get());
122       return true;
123     }
124   }
125   return false;
126 }
127 
SetValueSInt8(CFStringRef key,int8_t value,bool can_create)128 bool CFCMutableDictionary::SetValueSInt8(CFStringRef key, int8_t value,
129                                          bool can_create) {
130   CFMutableDictionaryRef dict = Dictionary(can_create);
131   if (dict != NULL) {
132     CFCReleaser<CFNumberRef> cf_number(
133         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt8Type, &value));
134     if (cf_number.get()) {
135       // Let the dictionary own the CFNumber
136       ::CFDictionarySetValue(dict, key, cf_number.get());
137       return true;
138     }
139   }
140   return false;
141 }
142 
AddValueSInt16(CFStringRef key,int16_t value,bool can_create)143 bool CFCMutableDictionary::AddValueSInt16(CFStringRef key, int16_t value,
144                                           bool can_create) {
145   CFMutableDictionaryRef dict = Dictionary(can_create);
146   if (dict != NULL) {
147     CFCReleaser<CFNumberRef> cf_number(
148         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt16Type, &value));
149     if (cf_number.get()) {
150       // Let the dictionary own the CFNumber
151       ::CFDictionaryAddValue(dict, key, cf_number.get());
152       return true;
153     }
154   }
155   return false;
156 }
157 
SetValueSInt16(CFStringRef key,int16_t value,bool can_create)158 bool CFCMutableDictionary::SetValueSInt16(CFStringRef key, int16_t value,
159                                           bool can_create) {
160   CFMutableDictionaryRef dict = Dictionary(can_create);
161   if (dict != NULL) {
162     CFCReleaser<CFNumberRef> cf_number(
163         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt16Type, &value));
164     if (cf_number.get()) {
165       // Let the dictionary own the CFNumber
166       ::CFDictionarySetValue(dict, key, cf_number.get());
167       return true;
168     }
169   }
170   return false;
171 }
172 
AddValueSInt32(CFStringRef key,int32_t value,bool can_create)173 bool CFCMutableDictionary::AddValueSInt32(CFStringRef key, int32_t value,
174                                           bool can_create) {
175   CFMutableDictionaryRef dict = Dictionary(can_create);
176   if (dict != NULL) {
177     CFCReleaser<CFNumberRef> cf_number(
178         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &value));
179     if (cf_number.get()) {
180       // Let the dictionary own the CFNumber
181       ::CFDictionaryAddValue(dict, key, cf_number.get());
182       return true;
183     }
184   }
185   return false;
186 }
187 
SetValueSInt32(CFStringRef key,int32_t value,bool can_create)188 bool CFCMutableDictionary::SetValueSInt32(CFStringRef key, int32_t value,
189                                           bool can_create) {
190   CFMutableDictionaryRef dict = Dictionary(can_create);
191   if (dict != NULL) {
192     CFCReleaser<CFNumberRef> cf_number(
193         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &value));
194     if (cf_number.get()) {
195       // Let the dictionary own the CFNumber
196       ::CFDictionarySetValue(dict, key, cf_number.get());
197       return true;
198     }
199   }
200   return false;
201 }
202 
AddValueSInt64(CFStringRef key,int64_t value,bool can_create)203 bool CFCMutableDictionary::AddValueSInt64(CFStringRef key, int64_t value,
204                                           bool can_create) {
205   CFMutableDictionaryRef dict = Dictionary(can_create);
206   if (dict != NULL) {
207     CFCReleaser<CFNumberRef> cf_number(
208         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt64Type, &value));
209     if (cf_number.get()) {
210       // Let the dictionary own the CFNumber
211       ::CFDictionaryAddValue(dict, key, cf_number.get());
212       return true;
213     }
214   }
215   return false;
216 }
217 
SetValueSInt64(CFStringRef key,int64_t value,bool can_create)218 bool CFCMutableDictionary::SetValueSInt64(CFStringRef key, int64_t value,
219                                           bool can_create) {
220   CFMutableDictionaryRef dict = Dictionary(can_create);
221   if (dict != NULL) {
222     CFCReleaser<CFNumberRef> cf_number(
223         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt64Type, &value));
224     if (cf_number.get()) {
225       // Let the dictionary own the CFNumber
226       ::CFDictionarySetValue(dict, key, cf_number.get());
227       return true;
228     }
229   }
230   return false;
231 }
232 
AddValueUInt8(CFStringRef key,uint8_t value,bool can_create)233 bool CFCMutableDictionary::AddValueUInt8(CFStringRef key, uint8_t value,
234                                          bool can_create) {
235   CFMutableDictionaryRef dict = Dictionary(can_create);
236   if (dict != NULL) {
237     // Have to promote to the next size type so things don't appear negative of
238     // the MSBit is set...
239     int16_t sval = value;
240     CFCReleaser<CFNumberRef> cf_number(
241         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt16Type, &sval));
242     if (cf_number.get()) {
243       // Let the dictionary own the CFNumber
244       ::CFDictionaryAddValue(dict, key, cf_number.get());
245       return true;
246     }
247   }
248   return false;
249 }
250 
SetValueUInt8(CFStringRef key,uint8_t value,bool can_create)251 bool CFCMutableDictionary::SetValueUInt8(CFStringRef key, uint8_t value,
252                                          bool can_create) {
253   CFMutableDictionaryRef dict = Dictionary(can_create);
254   if (dict != NULL) {
255     // Have to promote to the next size type so things don't appear negative of
256     // the MSBit is set...
257     int16_t sval = value;
258     CFCReleaser<CFNumberRef> cf_number(
259         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt16Type, &sval));
260     if (cf_number.get()) {
261       // Let the dictionary own the CFNumber
262       ::CFDictionarySetValue(dict, key, cf_number.get());
263       return true;
264     }
265   }
266   return false;
267 }
268 
AddValueUInt16(CFStringRef key,uint16_t value,bool can_create)269 bool CFCMutableDictionary::AddValueUInt16(CFStringRef key, uint16_t value,
270                                           bool can_create) {
271   CFMutableDictionaryRef dict = Dictionary(can_create);
272   if (dict != NULL) {
273     // Have to promote to the next size type so things don't appear negative of
274     // the MSBit is set...
275     int32_t sval = value;
276     CFCReleaser<CFNumberRef> cf_number(
277         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &sval));
278     if (cf_number.get()) {
279       // Let the dictionary own the CFNumber
280       ::CFDictionaryAddValue(dict, key, cf_number.get());
281       return true;
282     }
283   }
284   return false;
285 }
286 
SetValueUInt16(CFStringRef key,uint16_t value,bool can_create)287 bool CFCMutableDictionary::SetValueUInt16(CFStringRef key, uint16_t value,
288                                           bool can_create) {
289   CFMutableDictionaryRef dict = Dictionary(can_create);
290   if (dict != NULL) {
291     // Have to promote to the next size type so things don't appear negative of
292     // the MSBit is set...
293     int32_t sval = value;
294     CFCReleaser<CFNumberRef> cf_number(
295         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &sval));
296     if (cf_number.get()) {
297       // Let the dictionary own the CFNumber
298       ::CFDictionarySetValue(dict, key, cf_number.get());
299       return true;
300     }
301   }
302   return false;
303 }
304 
AddValueUInt32(CFStringRef key,uint32_t value,bool can_create)305 bool CFCMutableDictionary::AddValueUInt32(CFStringRef key, uint32_t value,
306                                           bool can_create) {
307   CFMutableDictionaryRef dict = Dictionary(can_create);
308   if (dict != NULL) {
309     // Have to promote to the next size type so things don't appear negative of
310     // the MSBit is set...
311     int64_t sval = value;
312     CFCReleaser<CFNumberRef> cf_number(
313         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt64Type, &sval));
314     if (cf_number.get()) {
315       // Let the dictionary own the CFNumber
316       ::CFDictionaryAddValue(dict, key, cf_number.get());
317       return true;
318     }
319   }
320   return false;
321 }
322 
SetValueUInt32(CFStringRef key,uint32_t value,bool can_create)323 bool CFCMutableDictionary::SetValueUInt32(CFStringRef key, uint32_t value,
324                                           bool can_create) {
325   CFMutableDictionaryRef dict = Dictionary(can_create);
326   if (dict != NULL) {
327     // Have to promote to the next size type so things don't appear negative of
328     // the MSBit is set...
329     int64_t sval = value;
330     CFCReleaser<CFNumberRef> cf_number(
331         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt64Type, &sval));
332     if (cf_number.get()) {
333       // Let the dictionary own the CFNumber
334       ::CFDictionarySetValue(dict, key, cf_number.get());
335       return true;
336     }
337   }
338   return false;
339 }
340 
AddValueUInt64(CFStringRef key,uint64_t value,bool can_create)341 bool CFCMutableDictionary::AddValueUInt64(CFStringRef key, uint64_t value,
342                                           bool can_create) {
343   CFMutableDictionaryRef dict = Dictionary(can_create);
344   if (dict != NULL) {
345     // The number may appear negative if the MSBit is set in "value". Due to a
346     // limitation of CFNumber, there isn't a way to have it show up otherwise
347     // as of this writing.
348     CFCReleaser<CFNumberRef> cf_number(
349         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt64Type, &value));
350     if (cf_number.get()) {
351       // Let the dictionary own the CFNumber
352       ::CFDictionaryAddValue(dict, key, cf_number.get());
353       return true;
354     }
355   }
356   return false;
357 }
358 
SetValueUInt64(CFStringRef key,uint64_t value,bool can_create)359 bool CFCMutableDictionary::SetValueUInt64(CFStringRef key, uint64_t value,
360                                           bool can_create) {
361   CFMutableDictionaryRef dict = Dictionary(can_create);
362   if (dict != NULL) {
363     // The number may appear negative if the MSBit is set in "value". Due to a
364     // limitation of CFNumber, there isn't a way to have it show up otherwise
365     // as of this writing.
366     CFCReleaser<CFNumberRef> cf_number(
367         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt64Type, &value));
368     if (cf_number.get()) {
369       // Let the dictionary own the CFNumber
370       ::CFDictionarySetValue(dict, key, cf_number.get());
371       return true;
372     }
373   }
374   return false;
375 }
376 
AddValueDouble(CFStringRef key,double value,bool can_create)377 bool CFCMutableDictionary::AddValueDouble(CFStringRef key, double value,
378                                           bool can_create) {
379   CFMutableDictionaryRef dict = Dictionary(can_create);
380   if (dict != NULL) {
381     // The number may appear negative if the MSBit is set in "value". Due to a
382     // limitation of CFNumber, there isn't a way to have it show up otherwise
383     // as of this writing.
384     CFCReleaser<CFNumberRef> cf_number(
385         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberDoubleType, &value));
386     if (cf_number.get()) {
387       // Let the dictionary own the CFNumber
388       ::CFDictionaryAddValue(dict, key, cf_number.get());
389       return true;
390     }
391   }
392   return false;
393 }
394 
SetValueDouble(CFStringRef key,double value,bool can_create)395 bool CFCMutableDictionary::SetValueDouble(CFStringRef key, double value,
396                                           bool can_create) {
397   CFMutableDictionaryRef dict = Dictionary(can_create);
398   if (dict != NULL) {
399     // The number may appear negative if the MSBit is set in "value". Due to a
400     // limitation of CFNumber, there isn't a way to have it show up otherwise
401     // as of this writing.
402     CFCReleaser<CFNumberRef> cf_number(
403         ::CFNumberCreate(kCFAllocatorDefault, kCFNumberDoubleType, &value));
404     if (cf_number.get()) {
405       // Let the dictionary own the CFNumber
406       ::CFDictionarySetValue(dict, key, cf_number.get());
407       return true;
408     }
409   }
410   return false;
411 }
412 
AddValueCString(CFStringRef key,const char * cstr,bool can_create)413 bool CFCMutableDictionary::AddValueCString(CFStringRef key, const char *cstr,
414                                            bool can_create) {
415   CFMutableDictionaryRef dict = Dictionary(can_create);
416   if (dict != NULL) {
417     CFCString cf_str(cstr, kCFStringEncodingUTF8);
418     if (cf_str.get()) {
419       // Let the dictionary own the CFNumber
420       ::CFDictionaryAddValue(dict, key, cf_str.get());
421       return true;
422     }
423   }
424   return false;
425 }
426 
SetValueCString(CFStringRef key,const char * cstr,bool can_create)427 bool CFCMutableDictionary::SetValueCString(CFStringRef key, const char *cstr,
428                                            bool can_create) {
429   CFMutableDictionaryRef dict = Dictionary(can_create);
430   if (dict != NULL) {
431     CFCString cf_str(cstr, kCFStringEncodingUTF8);
432     if (cf_str.get()) {
433       // Let the dictionary own the CFNumber
434       ::CFDictionarySetValue(dict, key, cf_str.get());
435       return true;
436     }
437   }
438   return false;
439 }
440 
RemoveAllValues()441 void CFCMutableDictionary::RemoveAllValues() {
442   CFMutableDictionaryRef dict = get();
443   if (dict)
444     ::CFDictionaryRemoveAllValues(dict);
445 }
446 
RemoveValue(const void * value)447 void CFCMutableDictionary::RemoveValue(const void *value) {
448   CFMutableDictionaryRef dict = get();
449   if (dict)
450     ::CFDictionaryRemoveValue(dict, value);
451 }
ReplaceValue(const void * key,const void * value)452 void CFCMutableDictionary::ReplaceValue(const void *key, const void *value) {
453   CFMutableDictionaryRef dict = get();
454   if (dict)
455     ::CFDictionaryReplaceValue(dict, key, value);
456 }
457