xref: /xnu-10063.101.15/libkern/libkern/c++/OSDictionary.h (revision 94d3b452840153a99b38a3a9659680b2a006908e)
1 /*
2  * Copyright (c) 2019 Apple Inc. All rights reserved.
3  *
4  * @APPLE_OSREFERENCE_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. The rights granted to you under the License
10  * may not be used to create, or enable the creation or redistribution of,
11  * unlawful or unlicensed copies of an Apple operating system, or to
12  * circumvent, violate, or enable the circumvention or violation of, any
13  * terms of an Apple operating system software license agreement.
14  *
15  * Please obtain a copy of the License at
16  * http://www.opensource.apple.com/apsl/ and read it before using this file.
17  *
18  * The Original Code and all software distributed under the License are
19  * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
20  * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
21  * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
22  * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
23  * Please see the License for the specific language governing rights and
24  * limitations under the License.
25  *
26  * @APPLE_OSREFERENCE_LICENSE_HEADER_END@
27  */
28 /*
29  * Copyright (c) 1998-1999 Apple Computer, Inc.  All rights reserved.
30  *
31  * HISTORY
32  *
33  * OSDictionary.h created by rsulack on Wed 17-Sep-1997
34  * OSDictionary.h converted to C++ by gvdl on Fri 1998-10-30
35  */
36 
37 #ifndef _IOKIT_IODICTIONARY_H
38 #define _IOKIT_IODICTIONARY_H
39 
40 #include <libkern/c++/OSCollection.h>
41 #include <libkern/c++/OSArray.h>
42 #include <libkern/c++/OSPtr.h>
43 #include <os/base.h>
44 
45 class OSArray;
46 class OSSymbol;
47 class OSString;
48 class OSDictionary;
49 
50 typedef OSDictionary* OSDictionaryPtr;
51 
52 /*!
53  * @header
54  *
55  * @abstract
56  * This header declares the OSDictionary collection class.
57  */
58 
59 
60 /*!
61  * @class OSDictionary
62  *
63  * @abstract
64  * OSDictionary provides an associative store using strings for keys.
65  *
66  * @discussion
67  * OSDictionary is a container for Libkern C++ objects
68  * (those derived from
69  * @link //apple_ref/doc/class/OSMetaClassBase OSMetaClassBase@/link,
70  * in particular @link //apple_ref/doc/class/OSObject OSObject@/link).
71  * Storage and access are associative, based on string-valued keys
72  * (C string, @link //apple_ref/cpp/cl/OSString OSString@/link,
73  * or @link //apple_ref/cpp/cl/OSSymbol OSSymbol@/link).
74  * When adding an object to an OSDictionary, you provide a string identifier,
75  * which can then used to retrieve that object or remove it from the dictionary.
76  * Setting an object with a key that already has an associated object
77  * replaces the original object.
78  *
79  * You must generally cast retrieved objects from
80  * @link //apple_ref/cpp/cl/OSObject OSObject@/link
81  * to the desired class using
82  * <code>@link //apple_ref/cpp/macro/OSDynamicCast OSDynamicCast@/link</code>.
83  * This macro returns the object cast to the desired class,
84  * or <code>NULL</code> if the object isn't derived from that class.
85  *
86  * When iterating an OSDictionary using
87  * @link //apple_ref/doc/class/OSCollectionIterator OSCollectionIterator@/link,
88  * the objects returned from
89  * <code>@link //apple_ref/doc/function/OSCollectionIterator::getNextObject
90  * getNextObject@/link</code>
91  * are dictionary keys (not the object values for those keys).
92  * You can use the keys to retrieve their associated object values.
93  *
94  * As with all Libkern collection classes,
95  * OSDictionary retains keys and objects added to it,
96  * and releases keys and objects removed from it (or replaced).
97  * An OSDictionary also grows as necessary to accommodate new key/value pairs,
98  * <i>unlike</i> Core Foundation collections (it does not, however, shrink).
99  *
100  * <b>Note:</b> OSDictionary currently uses a linear search algorithm,
101  * and is not designed for high-performance access of many values.
102  * It is intended as a simple associative-storage mechanism only.
103  *
104  * <b>Use Restrictions</b>
105  *
106  * With very few exceptions in the I/O Kit, all Libkern-based C++
107  * classes, functions, and macros are <b>unsafe</b>
108  * to use in a primary interrupt context.
109  * Consult the I/O Kit documentation related to primary interrupts
110  * for more information.
111  *
112  * OSDictionary provides no concurrency protection;
113  * it's up to the usage context to provide any protection necessary.
114  * Some portions of the I/O Kit, such as
115  * @link //apple_ref/doc/class/IORegistryEntry IORegistryEntry@/link,
116  * handle synchronization via defined member functions for setting
117  * properties.
118  */
119 class OSDictionary : public OSCollection
120 {
121 	friend class OSSerialize;
122 
123 	OSDeclareDefaultStructors(OSDictionary);
124 
125 #if APPLE_KEXT_ALIGN_CONTAINERS
126 
127 protected:
128 	unsigned int   count;
129 	unsigned int   capacity;
130 	unsigned int   capacityIncrement;
131 	struct dictEntry {
132 		OSTaggedPtr<const OSSymbol>        key;
133 		OSTaggedPtr<const OSMetaClassBase> value;
134 #if XNU_KERNEL_PRIVATE
135 		static int compare(const void *, const void *);
136 #endif
137 	};
138 	dictEntry    * OS_PTRAUTH_SIGNED_PTR("OSDictionary.dictionary") dictionary;
139 
140 #else /* APPLE_KEXT_ALIGN_CONTAINERS */
141 
142 protected:
143 	struct dictEntry {
144 		OSTaggedPtr<const OSSymbol>        key;
145 		OSTaggedPtr<const OSMetaClassBase> value;
146 #if XNU_KERNEL_PRIVATE
147 		static int compare(const void *, const void *);
148 #endif
149 	};
150 	dictEntry    * OS_PTRAUTH_SIGNED_PTR("OSDictionary.dictionary") dictionary;
151 	unsigned int   count;
152 	unsigned int   capacity;
153 	unsigned int   capacityIncrement;
154 
155 	struct ExpansionData { };
156 
157 /* Reserved for future use.  (Internal use only)  */
158 	ExpansionData * reserved;
159 
160 #endif /* APPLE_KEXT_ALIGN_CONTAINERS */
161 
162 // Member functions used by the OSCollectionIterator class.
163 	virtual unsigned int iteratorSize() const APPLE_KEXT_OVERRIDE;
164 	virtual bool initIterator(void * iterator) const APPLE_KEXT_OVERRIDE;
165 	virtual bool getNextObjectForIterator(void * iterator, OSObject ** ret) const APPLE_KEXT_OVERRIDE;
166 
167 public:
168 
169 /*!
170  * @function withCapacity
171  *
172  * @abstract
173  * Creates and initializes an empty OSDictionary.
174  *
175  * @param  capacity  The initial storage capacity of the new dictionary object.
176  *
177  * @result
178  * An empty instance of OSDictionary
179  * with a retain count of 1;
180  * <code>NULL</code> on failure.
181  *
182  * @discussion
183  * <code>capacity</code> must be nonzero.
184  * The new dictionary will grow as needed to accommodate more key/object pairs
185  * (<i>unlike</i> @link //apple_ref/doc/uid/20001497 CFMutableDictionary@/link,
186  * for which the initial capacity is a hard limit).
187  */
188 	static OSPtr<OSDictionary> withCapacity(unsigned int capacity);
189 
190 
191 /*!
192  * @function withObjects
193  *
194  * @abstract Creates and initializes an OSDictionary
195  *           populated with keys and objects provided.
196  *
197  * @param objects   A C array of OSMetaClassBase-derived objects.
198  * @param keys      A C array of OSSymbol keys
199  *                  for the corresponding objects in <code>objects</code>.
200  * @param count     The number of keys and objects
201  *                  to be placed into the dictionary.
202  * @param capacity  The initial storage capacity of the new dictionary object.
203  *                  If 0, <code>count</code> is used; otherwise this value
204  *                  must be greater than or equal to <code>count</code>.
205  *
206  * @result
207  * An instance of OSDictionary
208  * containing the key/object pairs provided,
209  * with a retain count of 1;
210  * <code>NULL</code> on failure.
211  *
212  * @discussion
213  * <code>objects</code> and <code>keys</code> must be non-<code>NULL</code>,
214  * and <code>count</code> must be nonzero.
215  * If <code>capacity</code> is nonzero,
216  * it must be greater than or equal to <code>count</code>.
217  * The new dictionary will grow as needed
218  * to accommodate more key/object pairs
219  * (<i>unlike</i>
220  * @link //apple_ref/doc/uid/20001497 CFMutableDictionary@/link,
221  * for which the initial capacity is a hard limit).
222  */
223 	static OSPtr<OSDictionary> withObjects(
224 		const OSObject * objects[],
225 		const OSSymbol * keys[],
226 		unsigned int     count,
227 		unsigned int     capacity = 0);
228 
229 /*!
230  * @function withObjects
231  *
232  * @abstract
233  * Creates and initializes an OSDictionary
234  * populated with keys and objects provided.
235  *
236  * @param objects   A C array of OSMetaClassBase-derived objects.
237  * @param keys      A C array of OSString keys for the corresponding objects
238  *                  in <code>objects</code>.
239  * @param count     The number of keys and objects
240  *                  to be placed into the dictionary.
241  * @param capacity  The initial storage capacity of the new dictionary object.
242  *                  If 0, <code>count</code> is used; otherwise this value
243  *                  must be greater than or equal to <code>count</code>.
244  *
245  * @result
246  * An instance of OSDictionary
247  * containing the key/object pairs provided,
248  * with a retain count of 1;
249  * <code>NULL</code> on failure.
250  *
251  * @discussion
252  * <code>objects</code> and <code>keys</code> must be non-<code>NULL</code>,
253  * and <code>count</code> must be nonzero.
254  * If <code>capacity</code> is nonzero, it must be greater than or equal to <code>count</code>.
255  * The new dictionary will grow as needed
256  * to accommodate more key/object pairs
257  * (<i>unlike</i>
258  * @link //apple_ref/doc/uid/20001497 CFMutableDictionary@/link,
259  * for which the initial capacity is a hard limit).
260  */
261 	static OSPtr<OSDictionary> withObjects(
262 		const OSObject * objects[],
263 		const OSString * keys[],
264 		unsigned int     count,
265 		unsigned int     capacity = 0);
266 
267 
268 /*!
269  * @function withDictionary
270  *
271  * @abstract
272  * Creates and initializes an OSDictionary
273  * populated with the contents of another dictionary.
274  *
275  * @param dict      A dictionary whose contents will be stored
276  *                  in the new instance.
277  * @param capacity  The initial storage capacity of the new dictionary object.
278  *                  If 0, the capacity is set to the number of key/value pairs
279  *                  in <code>dict</code>;
280  *                  otherwise <code>capacity</code> must be greater than or equal to
281  *                  the number of key/value pairs in <code>dict</code>.
282  *
283  * @result
284  * An instance of OSDictionary
285  * containing the key/value pairs of <code>dict</code>,
286  * with a retain count of 1;
287  * <code>NULL</code> on failure.
288  *
289  * @discussion
290  * <code>dict</code> must be non-<code>NULL</code>.
291  * If <code>capacity</code> is nonzero, it must be greater than or equal to <code>count</code>.
292  * The new dictionary will grow as needed
293  * to accommodate more key/object pairs
294  * (<i>unlike</i>
295  *  @link //apple_ref/doc/uid/20001497 CFMutableDictionary@/link,
296  * for which the initial capacity is a hard limit).
297  *
298  * The keys and objects in <code>dict</code> are retained for storage
299  * in the new OSDictionary,
300  * not copied.
301  */
302 	static OSPtr<OSDictionary> withDictionary(
303 		const OSDictionary * dict,
304 		unsigned int         capacity = 0);
305 
306 
307 /*!
308  * @function initWithCapacity
309  *
310  * @abstract
311  * Initializes a new instance of OSDictionary.
312  *
313  * @param capacity  The initial storage capacity of the new dictionary object.
314  * @result
315  * <code>true</code> on success, <code>false</code> on failure.
316  *
317  * @discussion
318  * Not for general use. Use the static instance creation method
319  * <code>@link //apple_ref/cpp/clm/OSDictionary/withCapacity/staticOSDictionary*\/(unsignedint)
320  * withCapacity@/link</code>
321  * instead.
322  *
323  * <code>capacity</code> must be nonzero.
324  * The new dictionary will grow as needed
325  * to accommodate more key/object pairs
326  * (<i>unlike</i>
327  * @link //apple_ref/doc/uid/20001497 CFMutableDictionary@/link,
328  * for which the initial capacity is a hard limit).
329  */
330 	virtual bool initWithCapacity(unsigned int capacity);
331 
332 
333 /*!
334  * @function initWithObjects
335  *
336  * @abstract Initializes a new OSDictionary with keys and objects provided.
337  *
338  * @param objects   A C array of OSMetaClassBase-derived objects.
339  * @param keys      A C array of OSSymbol keys
340  *                  for the corresponding objects in <code>objects</code>.
341  * @param count     The number of keys and objects to be placed
342  *                  into the dictionary.
343  * @param capacity  The initial storage capacity of the new dictionary object.
344  *                  If 0, <code>count</code> is used; otherwise this value
345  *                  must be greater than or equal to <code>count</code>.
346  *
347  * @result
348  * <code>true</code> on success, <code>false</code> on failure.
349  *
350  * @discussion
351  * Not for general use. Use the static instance creation method
352  * <code>@link
353  * //apple_ref/cpp/clm/OSDictionary/withObjects/staticOSDictionary*\/(constOSObject*,constOSString*,unsignedint,unsignedint)
354  * withObjects@/link</code>
355  * instead.
356  *
357  * <code>objects</code> and <code>keys</code> must be non-<code>NULL</code>,
358  * and <code>count</code> must be nonzero.
359  * If <code>capacity</code> is nonzero,
360  * it must be greater than or equal to <code>count</code>.
361  * The new dictionary will grow as neede
362  * to accommodate more key/object pairs
363  * (<i>unlike</i>
364  * @link //apple_ref/doc/uid/20001497 CFMutableDictionary@/link,
365  * for which the initial capacity is a hard limit).
366  */
367 	virtual bool initWithObjects(
368 		const OSObject * objects[],
369 		const OSSymbol * keys[],
370 		unsigned int     count,
371 		unsigned int     capacity = 0);
372 
373 
374 /*!
375  * @function initWithObjects
376  *
377  * @abstract
378  * Initializes a new OSDictionary with keys and objects provided.
379  *
380  * @param objects   A C array of OSMetaClassBase-derived objects.
381  * @param keys      A C array of OSString keys
382  *                  for the corresponding objects in <code>objects</code>.
383  * @param count     The number of keys and objects
384  *                  to be placed into the dictionary.
385  * @param capacity  The initial storage capacity of the new dictionary object.
386  *                  If 0, <code>count</code> is used; otherwise this value
387  *                  must be greater than or equal to <code>count</code>.
388  *
389  * @result
390  * <code>true</code> on success, <code>false</code> on failure.
391  *
392  * @discussion
393  * Not for general use. Use the static instance creation method
394  * <code>@link
395  * //apple_ref/cpp/clm/OSDictionary/withObjects/staticOSDictionary*\/(constOSObject*,constOSString*,unsignedint,unsignedint)
396  * withObjects@/link</code>
397  * instead.
398  *
399  * <code>objects</code> and <code>keys</code> must be non-<code>NULL</code>,
400  * and <code>count</code> must be nonzero.
401  * If <code>capacity</code> is nonzero, it must be greater than or equal to <code>count</code>.
402  * The new dictionary will grow as needed
403  * to accommodate more key/object pairs
404  * (<i>unlike</i>
405  * @link //apple_ref/doc/uid/20001497 CFMutableDictionary@/link,
406  * for which the initial capacity is a hard limit).
407  */
408 	virtual bool initWithObjects(
409 		const OSObject * objects[],
410 		const OSString * keys[],
411 		unsigned int     count,
412 		unsigned int     capacity = 0);
413 
414 
415 /*!
416  * @function initWithDictionary
417  *
418  * @abstract
419  * Initializes a new OSDictionary
420  * with the contents of another dictionary.
421  *
422  * @param dict      A dictionary whose contents will be placed
423  *                  in the new instance.
424  * @param capacity  The initial storage capacity of the new dictionary object.
425  *                  If 0, the capacity is set to the number of key/value pairs
426  *                  in <code>dict</code>;
427  *                  otherwise <code>capacity</code> must be greater than or equal to
428  *                  the number of key/value pairs in <code>dict</code>.
429  *
430  * @result
431  * <code>true</code> on success, <code>false</code> on failure.
432  *
433  * @discussion
434  * Not for general use. Use the static instance creation method
435  * <code>@link withDictionary withDictionary@/link</code> instead.
436  *
437  * <code>dict</code> must be non-<code>NULL</code>.
438  * If <code>capacity</code> is nonzero,
439  * it must be greater than or equal to <code>count</code>.
440  * The new dictionary will grow as needed
441  * to accommodate more key/object pairs
442  * (<i>unlike</i>
443  * @link //apple_ref/doc/uid/20001497 CFMutableDictionary@/link,
444  * for which the initial capacity is a hard limit).
445  *
446  * The keys and objects in <code>dict</code> are retained for storage
447  * in the new OSDictionary,
448  * not copied.
449  */
450 	virtual bool initWithDictionary(
451 		const OSDictionary * dict,
452 		unsigned int         capacity = 0);
453 
454 
455 /*!
456  * @function free
457  *
458  * @abstract
459  * Deallocates or releases any resources
460  * used by the OSDictionary instance.
461  *
462  * @discussion
463  * This function should not be called directly,
464  * use
465  * <code>@link
466  * //apple_ref/cpp/instm/OSObject/release/virtualvoid/()
467  * release@/link</code>
468  * instead.
469  */
470 	virtual void free() APPLE_KEXT_OVERRIDE;
471 
472 
473 /*!
474  * @function getCount
475  *
476  * @abstract
477  * Returns the current number of key/object pairs
478  * contained within the dictionary.
479  *
480  * @result
481  * The current number of key/object pairs
482  * contained within the dictionary.
483  */
484 	virtual unsigned int getCount() const APPLE_KEXT_OVERRIDE;
485 
486 
487 /*!
488  * @function getCapacity
489  *
490  * @abstract
491  * Returns the number of objects the dictionary can store without reallocating.
492  *
493  * @result
494  * The number objects the dictionary can store without reallocating.
495  *
496  * @discussion
497  * OSDictionary objects grow when full
498  * to accommodate additional key/object pairs.
499  * See
500  * <code>@link
501  * //apple_ref/cpp/instm/OSDictionary/getCapacityIncrement/virtualunsignedint/()
502  * getCapacityIncrement@/link</code>
503  * and
504  * <code>@link
505  * //apple_ref/cpp/instm/OSDictionary/ensureCapacity/virtualunsignedint/(unsignedint)
506  * ensureCapacity@/link</code>.
507  */
508 	virtual unsigned int getCapacity() const APPLE_KEXT_OVERRIDE;
509 
510 
511 /*!
512  * @function getCapacityIncrement
513  *
514  * @abstract
515  * Returns the storage increment of the dictionary.
516  *
517  * @result
518  * The storage increment of the dictionary.
519  *
520  * @discussion
521  * An OSDictionary allocates storage for key/object pairs in multiples
522  * of the capacity increment.
523  */
524 	virtual unsigned int getCapacityIncrement() const APPLE_KEXT_OVERRIDE;
525 
526 
527 /*!
528  * @function setCapacityIncrement
529  *
530  * @abstract
531  * Sets the storage increment of the dictionary.
532  *
533  * @result
534  * The new storage increment of the dictionary,
535  * which may be different from the number requested.
536  *
537  * @discussion
538  * An OSDictionary allocates storage for key/object pairs in multiples
539  * of the capacity increment.
540  * Calling this function does not immediately reallocate storage.
541  */
542 	virtual unsigned int setCapacityIncrement(unsigned increment) APPLE_KEXT_OVERRIDE;
543 
544 
545 /*!
546  * @function ensureCapacity
547  *
548  * @abstract
549  * Ensures the dictionary has enough space
550  * to store the requested number of key/object  pairs.
551  *
552  * @param newCapacity  The total number of key/object pairs the dictionary
553  *                     should be able to store.
554  *
555  * @result
556  * The new capacity of the dictionary,
557  * which may be different from the number requested
558  * (if smaller, reallocation of storage failed).
559  *
560  * @discussion
561  * This function immediately resizes the dictionary, if necessary,
562  * to accommodate at least <code>newCapacity</code> key/object pairs.
563  * If <code>newCapacity</code> is not greater than the current capacity,
564  * or if an allocation error occurs, the original capacity is returned.
565  *
566  * There is no way to reduce the capacity of an OSDictionary.
567  */
568 	virtual unsigned int ensureCapacity(unsigned int newCapacity) APPLE_KEXT_OVERRIDE;
569 
570 
571 /*!
572  * @function flushCollection
573  *
574  * @abstract
575  * Removes and releases all keys and objects within the dictionary.
576  *
577  * @discussion
578  * The dictionary's capacity (and therefore direct memory consumption)
579  * is not reduced by this function.
580  */
581 	virtual void flushCollection() APPLE_KEXT_OVERRIDE;
582 
583 
584 /*!
585  * @function setObject
586  *
587  * @abstract
588  * Stores an object in the dictionary under a key.
589  *
590  * @param aKey      An OSSymbol identifying the object
591  *                  placed within the dictionary.
592  *                  It is automatically retained.
593  * @param anObject  The object to be stored in the dictionary.
594  *                  It is automatically retained.
595  *
596  * @result
597  * <code>true</code> if the addition was successful,
598  * <code>false</code> otherwise.
599  *
600  * @discussion
601  * An object already stored under <code>aKey</code> is released.
602  */
603 	virtual bool setObject(
604 		const OSSymbol        * aKey,
605 		const OSMetaClassBase * anObject);
606 
607 	bool setObject(
608 		OSSharedPtr<const OSSymbol> const& aKey,
609 		OSSharedPtr<const OSMetaClassBase> const& anObject);
610 
611 
612 /*!
613  * @function setObject
614  *
615  * @abstract Stores an object in the dictionary under a key.
616  *
617  * @param aKey      An OSString identifying the object
618  *                  placed within the dictionary.
619  * @param anObject  The object to be stored in the dictionary.
620  *                  It is automatically retained.
621  *
622  * @result
623  * <code>true</code> if the addition was successful,
624  * <code>false</code> otherwise.
625  *
626  * @discussion
627  * An OSSymbol for <code>aKey</code> is created internally.
628  * An object already stored under <code>aKey</code> is released.
629  */
630 	virtual bool setObject(
631 		const OSString        * aKey,
632 		const OSMetaClassBase * anObject);
633 
634 	bool setObject(
635 		const OSString        * aKey,
636 		OSSharedPtr<const OSMetaClassBase> const& anObject);
637 
638 
639 /*!
640  * @function setObject
641  *
642  * @abstract
643  * Stores an object in the dictionary under a key.
644  *
645  * @param aKey      A C string identifying the object
646  *                  placed within the dictionary.
647  * @param anObject  The object to be stored in the dictionary.
648  *                  It is automatically retained.
649  *
650  * @result
651  * <code>true</code> if the addition was successful,
652  * <code>false</code> otherwise.
653  *
654  * @discussion
655  * An OSSymbol for <code>aKey</code> is created internally.
656  * An object already stored under <code>aKey</code> is released.
657  */
658 	virtual bool setObject(
659 		const char            * aKey,
660 		const OSMetaClassBase * anObject);
661 
662 	bool setObject(
663 		const char            * aKey,
664 		OSSharedPtr<const OSMetaClassBase> const& anObject);
665 
666 
667 /*!
668  * @function removeObject
669  *
670  * @abstract
671  * Removes a key/object pair from the dictionary.
672  *
673  * @param aKey  An OSSymbol identifying the object
674  *              to be removed from the dictionary.
675  *
676  * @discussion
677  * The removed key (not necessarily <code>aKey</code> itself)
678  * and object are automatically released.
679  */
680 	virtual void removeObject(const OSSymbol * aKey);
681 
682 
683 /*!
684  * @function removeObject
685  *
686  * @abstract
687  * Removes a key/object pair from the dictionary.
688  *
689  * @param aKey  A OSString identifying the object
690  *              to be removed from the dictionary.
691  *
692  * @discussion
693  * The removed key (not necessarily <code>aKey</code> itself)
694  * and object are automatically released.
695  */
696 	virtual void removeObject(const OSString * aKey);
697 
698 
699 /*!
700  * @function removeObject
701  *
702  * @abstract
703  * Removes a key/object pair from the dictionary.
704  *
705  * @param aKey  A C string identifying the object
706  *              to be removed from the dictionary.
707  *
708  * @discussion
709  * The removed key (internally an OSSymbol)
710  * and object are automatically released.
711  */
712 	virtual void removeObject(const char * aKey);
713 
714 
715 /*!
716  * @function merge
717  *
718  * @abstract
719  * Merges the contents of a dictionary into the receiver.
720  *
721  * @param aDictionary  The dictionary whose contents
722  *                     are to be merged with the receiver.
723  * @result
724  * <code>true</code> if the merge succeeds, <code>false</code> otherwise.
725  *
726  * @discussion
727  * If there are keys in <code>aDictionary</code> that match keys
728  * in the receiving dictionary,
729  * then the objects in the receiver are replaced
730  * by those from <code>aDictionary</code>,
731  * and the replaced objects are released.
732  */
733 	virtual bool merge(const OSDictionary * aDictionary);
734 
735 
736 /*!
737  * @function getObject
738  *
739  * @abstract
740  * Returns the object stored under a given key.
741  *
742  * @param aKey  An OSSymbol key identifying the object
743  *              to be returned to the caller.
744  *
745  * @result
746  * The object stored under <code>aKey</code>,
747  * or <code>NULL</code> if the key does not exist in the dictionary.
748  *
749  * @discussion
750  * The returned object will be released if removed from the dictionary;
751  * if you plan to store the reference, you should call
752  * <code>@link
753  * //apple_ref/cpp/instm/OSObject/retain/virtualvoid/()
754  * retain@/link</code>
755  * on that object.
756  */
757 	virtual OSObject * getObject(const OSSymbol * aKey) const;
758 
759 
760 /*!
761  * @function getObject
762  *
763  * @abstract Returns the object stored under a given key.
764  *
765  * @param aKey  An OSString key identifying the object
766  *              to be returned to caller.
767  *
768  * @result
769  * The object stored under <code>aKey</code>,
770  * or <code>NULL</code> if the key does not exist in the dictionary.
771  *
772  * @discussion
773  * The returned object will be released if removed from the dictionary;
774  * if you plan to store the reference, you should call
775  * <code>@link
776  * //apple_ref/cpp/instm/OSObject/retain/virtualvoid/()
777  * retain@/link</code>
778  * on that object.
779  */
780 	virtual OSObject * getObject(const OSString * aKey) const;
781 
782 
783 /*!
784  * @function getObject
785  *
786  * @abstract
787  * Returns the object stored under a given key.
788  *
789  * @param aKey  A C string key identifying the object
790  *              to be returned to caller.
791  *
792  * @result
793  * The object stored under <code>aKey</code>,
794  * or <code>NULL</code> if the key does not exist in the dictionary.
795  *
796  * @discussion
797  * The returned object will be released if removed from the dictionary;
798  * if you plan to store the reference, you should call
799  * <code>@link
800  * //apple_ref/cpp/instm/OSObject/retain/virtualvoid/()
801  * retain@/link</code>
802  * on that object.
803  */
804 	virtual OSObject * getObject(const char * aKey) const;
805 
806 
807 /*!
808  * @function isEqualTo
809  *
810  * @abstract Tests the equality of two OSDictionary objects
811  * over a subset of keys.
812  *
813  * @param aDictionary  The dictionary to be compared against the receiver.
814  * @param keys         An OSArray or OSDictionary containing the keys
815  *                     (as @link //apple_ref/cpp/cl/OSString OSStrings@/link or
816  *                     @link //apple_ref/cpp/cl/OSSymbol OSSymbols@/link)
817  *                     describing the intersection for the comparison.
818  *
819  * @result
820  * <code>true</code> if the intersections
821  * of the two dictionaries are equal.
822  *
823  * @discussion
824  * Two OSDictionary objects are considered equal by this function
825  * if both have objects stored for all keys provided,
826  * and if the objects stored in each under
827  * a given key compare as equal using
828  * <code>@link
829  * //apple_ref/cpp/instm/OSMetaClassBase/isEqualTo/virtualbool/(constOSMetaClassBase*)
830  * isEqualTo@/link</code>.
831  */
832 	virtual bool isEqualTo(
833 		const OSDictionary * aDictionary,
834 		const OSCollection * keys) const;
835 
836 
837 /*!
838  * @function isEqualTo
839  *
840  * @abstract Tests the equality of two OSDictionary objects.
841  *
842  * @param aDictionary  The dictionary to be compared against the receiver.
843  *
844  * @result
845  * <code>true</code> if the dictionaries are equal,
846  * <code>false</code> if not.
847  *
848  * @discussion
849  * Two OSDictionary objects are considered equal if they have same count,
850  * the same keys, and if the objects stored in each under
851  * a given key compare as equal using
852  * <code>@link
853  * //apple_ref/cpp/instm/OSMetaClassBase/isEqualTo/virtualbool/(constOSMetaClassBase*)
854  * isEqualTo@/link</code>.
855  */
856 	virtual bool isEqualTo(const OSDictionary * aDictionary) const;
857 
858 
859 /*!
860  * @function isEqualTo
861  *
862  * @abstract
863  * Tests the equality of an OSDictionary to an arbitrary object.
864  *
865  * @param anObject An object to be compared against the receiver.
866  *
867  * @result
868  * <code>true</code> if the objects are equal.
869  *
870  * @discussion
871  * An OSDictionary is considered equal to another object
872  * if that object is derived from OSDictionary
873  * and contains the same or equivalent objects.
874  */
875 	virtual bool isEqualTo(const OSMetaClassBase * anObject) const APPLE_KEXT_OVERRIDE;
876 
877 
878 /*!
879  * @function serialize
880  *
881  * @abstract
882  * Archives the receiver into the provided
883  * @link //apple_ref/doc/class/OSSerialize OSSerialize@/link object.
884  *
885  * @param serializer  The OSSerialize object.
886  *
887  * @result
888  * <code>true</code> if serialization succeeds, <code>false</code> if not.
889  */
890 	virtual bool serialize(OSSerialize * serializer) const APPLE_KEXT_OVERRIDE;
891 
892 
893 /*!
894  * @function setOptions
895  *
896  * @abstract
897  * Recursively sets option bits in the dictionary
898  * and all child collections.
899  *
900  * @param options  A bitfield whose values turn the options on (1) or off (0).
901  * @param mask     A mask indicating which bits
902  *                 in <code>options</code> to change.
903  *                 Pass 0 to get the whole current options bitfield
904  *                 without changing any settings.
905  * @param context  Unused.
906  *
907  * @result
908  * The options bitfield as it was before the set operation.
909  *
910  * @discussion
911  * Kernel extensions should not call this function.
912  *
913  * Child collections' options are changed only if the receiving dictionary's
914  * options actually change.
915  */
916 	virtual unsigned setOptions(
917 		unsigned   options,
918 		unsigned   mask,
919 		void     * context = NULL) APPLE_KEXT_OVERRIDE;
920 
921 
922 /*!
923  * @function copyCollection
924  *
925  * @abstract
926  * Creates a deep copy of the dictionary
927  * and its child collections.
928  *
929  * @param cycleDict  A dictionary of all of the collections
930  *                   that have been copied so far,
931  *                   which is used to track circular references.
932  *                   To start the copy at the top level,
933  *                   pass <code>NULL</code>.
934  *
935  * @result
936  * The newly copied dictionary, with a retain count of 1,
937  * or <code>NULL</code> if there is insufficient memory to do the copy.
938  *
939  * @discussion
940  * The receiving dictionary, and any collections it contains, recursively,
941  * are copied.
942  * Objects that are not derived from OSCollection are retained
943  * rather than copied.
944  */
945 	OSPtr<OSCollection> copyCollection(OSDictionary * cycleDict = NULL) APPLE_KEXT_OVERRIDE;
946 
947 #if XNU_KERNEL_PRIVATE
948 	bool setObject(const OSSymbol *aKey, const OSMetaClassBase *anObject, bool onlyAdd);
949 	void sortBySymbol(void);
950 	OSPtr<OSArray> copyKeys(void);
951 #endif /* XNU_KERNEL_PRIVATE */
952 
953 
954 /*!
955  * @function iterateObjects
956  *
957  * @abstract
958  * Invoke a callback for each member of the collection.
959  *
960  * @param refcon   A reference constant for the callback.
961  * @param callback The callback function,
962  *                 called with the refcon and each member key & object
963  *                 of the dictionary in turn, on the callers thread.
964  *                 The callback should return true to early terminate
965  *                 the iteration, false otherwise.
966  *
967  * @result
968  * False if the dictionary iteration was made invalid
969  * (see OSCollectionIterator::isValid()) otherwise true.
970  */
971 	bool iterateObjects(void * refcon, bool (*callback)(void * refcon, const OSSymbol * key, OSObject * object));
972 
973 #ifdef __BLOCKS__
974 
975 /*!
976  * @function iterateObjects
977  *
978  * @abstract
979  * Invoke a block for each member of the collection.
980  *
981  * @param block    The block,
982  *                 called with the refcon and each member key & object
983  *                 of the dictionary in turn, on the callers thread.
984  *                 The callback should return true to early terminate
985  *                 the iteration, false otherwise.
986  *
987  * @result
988  * False if the dictionary iteration was made invalid
989  * (see OSCollectionIterator::isValid()) otherwise true.
990  */
991 	bool iterateObjects(bool (^block)(const OSSymbol * key, OSObject * object));
992 
993 #endif /* __BLOCKS__ */
994 
995 	OSMetaClassDeclareReservedUnused(OSDictionary, 0);
996 	OSMetaClassDeclareReservedUnused(OSDictionary, 1);
997 	OSMetaClassDeclareReservedUnused(OSDictionary, 2);
998 	OSMetaClassDeclareReservedUnused(OSDictionary, 3);
999 	OSMetaClassDeclareReservedUnused(OSDictionary, 4);
1000 	OSMetaClassDeclareReservedUnused(OSDictionary, 5);
1001 	OSMetaClassDeclareReservedUnused(OSDictionary, 6);
1002 	OSMetaClassDeclareReservedUnused(OSDictionary, 7);
1003 };
1004 
1005 #endif /* !_IOKIT_IODICTIONARY_H */
1006