]> git.saurik.com Git - apple/xnu.git/blob - libkern/libkern/c++/OSMetaClass.h
322e5238a2bdaffb6c8e1d650e7d7822abddd5c9
[apple/xnu.git] / libkern / libkern / c++ / OSMetaClass.h
1 /*
2 * Copyright (c) 2000-2016 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 #ifndef _LIBKERN_OSMETACLASS_H
29 #define _LIBKERN_OSMETACLASS_H
30
31 #include <sys/types.h>
32
33 #include <libkern/OSReturn.h>
34 #include <kern/debug.h>
35
36 class OSMetaClass;
37 class OSObject;
38 class OSString;
39 class OSSymbol;
40 class OSDictionary;
41 class OSSerialize;
42 #ifdef XNU_KERNEL_PRIVATE
43 class OSOrderedSet;
44 class OSCollection;
45 #endif /* XNU_KERNEL_PRIVATE */
46
47
48 /*!
49 * @header
50 *
51 * @abstract
52 * This header declares the OSMetaClassBase and OSMetaClass classes,
53 * which together form the basis of the Libkern and I/O Kit C++ class hierarchy
54 * and run-time type information facility.
55 */
56
57
58 /*! @parseOnly */
59 #define APPLE_KEXT_COMPATIBILITY
60
61 #ifdef XNU_KERNEL_PRIVATE
62
63 #ifdef CONFIG_EMBEDDED
64 #define APPLE_KEXT_VTABLE_PADDING 0
65 #else /* CONFIG_EMBEDDED */
66 /*! @parseOnly */
67 #define APPLE_KEXT_VTABLE_PADDING 1
68 #endif /* CONFIG_EMBEDDED */
69
70 #else /* XNU_KERNEL_PRIVATE */
71 #include <TargetConditionals.h>
72
73 #if TARGET_OS_EMBEDDED
74 #define APPLE_KEXT_VTABLE_PADDING 0
75 #else /* TARGET_OS_EMBEDDED */
76 /*! @parseOnly */
77 #define APPLE_KEXT_VTABLE_PADDING 1
78 #endif /* TARGET_OS_EMBEDDED */
79
80 #endif /* XNU_KERNEL_PRIVATE */
81
82 #define APPLE_KEXT_ALIGN_CONTAINERS (0 == APPLE_KEXT_VTABLE_PADDING)
83
84 #if defined(__LP64__)
85 /*! @parseOnly */
86 #define APPLE_KEXT_LEGACY_ABI 0
87 #elif defined(__arm__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 2))
88 #define APPLE_KEXT_LEGACY_ABI 0
89 #else
90 #define APPLE_KEXT_LEGACY_ABI 1
91 #endif
92
93 #if defined(__LP64__)
94 /*! @parseOnly */
95 #define APPLE_KEXT_COMPATIBILITY_VIRTUAL
96 #else
97 // private method made virtual only for binary compatibility
98 #define APPLE_KEXT_COMPATIBILITY_VIRTUAL virtual
99 #endif
100
101 /*! @parseOnly */
102 #define APPLE_KEXT_DEPRECATED __attribute__((deprecated))
103
104
105 #if __cplusplus >= 201103L
106 #define APPLE_KEXT_OVERRIDE override
107 #if defined(__LP64__)
108 #define APPLE_KEXT_COMPATIBILITY_OVERRIDE
109 #else
110 #define APPLE_KEXT_COMPATIBILITY_OVERRIDE APPLE_KEXT_OVERRIDE
111 #endif
112 #else
113 #define APPLE_KEXT_OVERRIDE
114 #define APPLE_KEXT_COMPATIBILITY_OVERRIDE
115 #endif
116
117
118 /*!
119 * @class OSMetaClassBase
120 *
121 * @abstract
122 * OSMetaClassBase is the abstract bootstrap class
123 * for the Libkern and I/O Kit run-time type information system.
124 *
125 * @discussion
126 * OSMetaClassBase is the abstract C++ root class
127 * underlying the entire Libkern and I/O Kit class hierarchy.
128 * It defines the run-time type information system,
129 * including dynamic class allocation and safe type-casting,
130 * as well as the abstract interface for reference counting
131 * and a few other utility functions.
132 * OSMetaClassBase is the immediate superclass of
133 * @link //apple_ref/doc/class/OSObject OSObject@/link and
134 * @link //apple_ref/doc/class/OSMetaClass OSMetaClass@/link;
135 * no other class should derive from OSMetaClassBase.
136 *
137 * For more information, see
138 * <i>@link //apple_ref/doc/uid/TP40002799
139 * I/O Kit Device Driver Design Guidelines@/link</i>.
140 *
141 * <b>Use by Kernel Extensions</b>
142 *
143 * Kernel Extensions should never interact directly with OSMetaClassBase,
144 * but they will find useful several macros that tie in
145 * to the run-time type information system, specifically:
146 * <ul>
147 * <li><code>@link OSTypeAlloc OSTypeAlloc@/link</code> - allocation of new instances</li>
148 * <li><code>@link OSDynamicCast OSDynamicCast@/link</code> - safe type casting</li>
149 * <li><code>@link OSCheckTypeInst OSCheckTypeInst@/link</code> -
150 * checking for inheritance/derivation</li>
151 * <li><code>@link OSMemberFunctionCast OSMemberFunctionCast@/link</code> -
152 * casting C++ member functions to C function pointers
153 * for registration as callbacks</li>
154 * </ul>
155 *
156 * See @link //apple_ref/doc/class/OSMetaClass OSMetaClass@/link
157 * for more run-time type information interfaces.
158 *
159 * <b>Use Restrictions</b>
160 *
161 * OSMetaClassBase should not be subclassed by kernel extensions,
162 * nor should kernel extensions call its run-time type functions directly.
163 *
164 * The run-time type functions and macros are <b>not safe</b>
165 * to call in a primary interrupt context.
166 *
167 * <b>Concurrency Protection</b>
168 *
169 * The run-time type macros and functions of OSMetaClassBase are thread-safe.
170 */
171 class OSMetaClassBase
172 {
173 public:
174
175
176 /*!
177 * @define OSTypeAlloc
178 * @hidecontents
179 *
180 * @abstract
181 * Allocates an instance of the named object class.
182 *
183 * @param type The name of the desired class to be created,
184 * as a raw token, <i>not</i> a string or macro.
185 *
186 * @result
187 * A pointer to the new, uninitialized object on success;
188 * <code>NULL</code> on failure.
189 *
190 * @discussion
191 * See also
192 * <code>@link
193 * //apple_ref/cpp/clm/OSMetaClass/allocClassWithName/staticOSObject*\/(constchar*)
194 * OSMetaClass::allocClassWithName(const char *)@/link</code>
195 * and
196 * <code>@link
197 * //apple_ref/cpp/instm/OSMetaClass/alloc/virtualOSObject*\/()
198 * OSMetaClass::alloc@/link</code>.
199 *
200 * The OSTypeAlloc macro is used to avoid binary compatibility difficulties
201 * presented by the C++ <code>new</code> operator.
202 */
203 #define OSTypeAlloc(type) ((type *) ((type::metaClass)->alloc()))
204
205
206 /*!
207 * @define OSTypeID
208 * @hidecontents
209 *
210 * @abstract
211 * Returns the type ID (metaclass) of a class based on its name.
212 *
213 * @param type The name of the desired class, as a raw token,
214 * <i>not</i> a string or macro.
215 *
216 * @result
217 * The unique type ID (metaclass) for the class.
218 *
219 * @discussion
220 * It is typically more useful to determine whether a class is derived
221 * from another; see
222 * <code>@link //apple_ref/cpp/macro/OSDynamicCast OSDynamicCast@/link</code>
223 * and
224 * <code>@link //apple_ref/cpp/macro/OSCheckTypeInst OSCheckTypeInst@/link</code>.
225 */
226 #define OSTypeID(type) (type::metaClass)
227
228
229 /*!
230 * @define OSTypeIDInst
231 * @hidecontents
232 *
233 * @abstract
234 * Returns the type ID (metaclass) for the class of an object instance.
235 *
236 * @param typeinst An instance of an OSObject subclass.
237 *
238 * @result
239 * The type ID of that object's class; that is, its metaclass.
240 *
241 * @discussion
242 * It is typically more useful to determine whether an object is derived
243 * from a particular class; see
244 * <code>@link //apple_ref/cpp/macro/OSDynamicCast OSDynamicCast@/link</code>
245 * and
246 * <code>@link //apple_ref/cpp/macro/OSCheckTypeInst OSCheckTypeInst@/link</code>.
247 */
248 #define OSTypeIDInst(typeinst) ((typeinst)->getMetaClass())
249
250
251 /*!
252 * @define OSDynamicCast
253 * @hidecontents
254 *
255 * @abstract
256 * Safe type-casting for Libkern C++ objects.
257 *
258 * @param type The name of the desired class type, as a raw token,
259 * <i>not</i> a string or macro.
260 * It is assumed you intend to cast to a pointer
261 * to an object of this type.
262 * Type qualifiers, such as <code>const</code>,
263 * are not recognized and will cause
264 * a (usually obscure) compile error.
265 * @param inst A pointer to the object instance to be cast.
266 * May be <code>NULL</code>.
267 *
268 * @result
269 * <code>inst</code> if it is non-<code>NULL</code>
270 * and derived from <code>type</code>;
271 * otherwise <code>NULL</code>.
272 *
273 * @discussion
274 * <code>OSDynamicCast</code> is a rough equivalent
275 * to the standard C++ RTTI <code>dynamic_cast&lt;T&gt;</code> operator.
276 * Your code should use this instead of raw C type-casting,
277 * and check the resulting value.
278 * If the result is non-<code>NULL</code>,
279 * the object is safe to use as the type-cast class;
280 * if the result is <code>NULL</code>,
281 * the object does not derive from the type-cast class
282 * and your code should take appropriate steps to handle the error.
283 */
284 #define OSDynamicCast(type, inst) \
285 ((type *) OSMetaClassBase::safeMetaCast((inst), OSTypeID(type)))
286
287
288 /*!
289 * @define OSCheckTypeInst
290 * @hidecontents
291 *
292 * @abstract
293 * Checks whether two objects are type-compatible.
294 *
295 * @param typeinst The reference object.
296 * @param inst The object to check for type compatibility.
297 *
298 * @result
299 * <code>true</code> if both <code>inst</code> and
300 * <code>typeinst</code> are non-<code>NULL</code>
301 * and <code>inst</code> is derived from the class of <code>typeinst</code>;
302 * otherwise <code>false</code>.
303 */
304 #define OSCheckTypeInst(typeinst, inst) \
305 OSMetaClassBase::checkTypeInst(inst, typeinst)
306
307 #define OSSafeRelease(inst) \
308 do { int OSSafeRelease __attribute__ ((deprecated("Use OSSafeReleaseNULL"))); (OSSafeRelease); \
309 if (inst) (inst)->release(); } while (0)
310
311 /*! @function OSSafeReleaseNULL
312 * @abstract Release an object if not <code>NULL</code>, then set it to <code>NULL</code>.
313 * @param inst Instance of an OSObject, may be <code>NULL</code>.
314 */
315 #define OSSafeReleaseNULL(inst) do { if (inst) (inst)->release(); (inst) = NULL; } while (0)
316
317 typedef void (*_ptf_t)(void);
318
319 #if APPLE_KEXT_LEGACY_ABI
320
321 // Arcane evil code interprets a C++ pointer to function as specified in the
322 // -fapple-kext ABI, i.e. the gcc-2.95 generated code. IT DOES NOT ALLOW
323 // the conversion of functions that are from MULTIPLY inherited classes.
324
325 static inline _ptf_t
326 _ptmf2ptf(const OSMetaClassBase *self, void (OSMetaClassBase::*func)(void))
327 {
328 union {
329 void (OSMetaClassBase::*fIn)(void);
330 struct { // Pointer to member function 2.95
331 unsigned short fToff;
332 short fVInd;
333 union {
334 _ptf_t fPFN;
335 short fVOff;
336 } u;
337 } fptmf2;
338 } map;
339
340 map.fIn = func;
341 if (map.fptmf2.fToff) {
342 panic("Multiple inheritance is not supported");
343 return 0;
344 } else if (map.fptmf2.fVInd < 0) {
345 // Not virtual, i.e. plain member func
346 return map.fptmf2.u.fPFN;
347 } else {
348 union {
349 const OSMetaClassBase *fObj;
350 _ptf_t **vtablep;
351 } u;
352 u.fObj = self;
353
354 // Virtual member function so dereference vtable
355 return (*u.vtablep)[map.fptmf2.fVInd - 1];
356 }
357 }
358
359 #else /* !APPLE_KEXT_LEGACY_ABI */
360 #if defined(__arm__) || defined(__arm64__)
361 typedef long int ptrdiff_t;
362 /*
363 * Ugly reverse engineered ABI. Where does it come from? Nobody knows.
364 * <rdar://problem/5641129> gcc 4.2-built ARM kernel panics with multiple inheritance (no, really)
365 */
366 static inline _ptf_t
367 _ptmf2ptf(const OSMetaClassBase *self, void (OSMetaClassBase::*func)(void))
368 {
369 struct ptmf_t {
370 _ptf_t fPFN;
371 ptrdiff_t delta;
372 };
373 union {
374 void (OSMetaClassBase::*fIn)(void);
375 struct ptmf_t pTMF;
376 } map;
377
378
379 map.fIn = func;
380
381 if (map.pTMF.delta & 1) {
382 // virtual
383 union {
384 const OSMetaClassBase *fObj;
385 _ptf_t **vtablep;
386 } u;
387 u.fObj = self;
388
389 // Virtual member function so dereference table
390 return *(_ptf_t *)(((uintptr_t)*u.vtablep) + (uintptr_t)map.pTMF.fPFN);
391 } else {
392 // Not virtual, i.e. plain member func
393 return map.pTMF.fPFN;
394 }
395 }
396 #elif defined(__i386__) || defined(__x86_64__)
397
398 // Slightly less arcane and slightly less evil code to do
399 // the same for kexts compiled with the standard Itanium C++
400 // ABI
401
402 static inline _ptf_t
403 _ptmf2ptf(const OSMetaClassBase *self, void (OSMetaClassBase::*func)(void))
404 {
405 union {
406 void (OSMetaClassBase::*fIn)(void);
407 uintptr_t fVTOffset;
408 _ptf_t fPFN;
409 } map;
410
411 map.fIn = func;
412
413 if (map.fVTOffset & 1) {
414 // virtual
415 union {
416 const OSMetaClassBase *fObj;
417 _ptf_t **vtablep;
418 } u;
419 u.fObj = self;
420
421 // Virtual member function so dereference vtable
422 return *(_ptf_t *)(((uintptr_t)*u.vtablep) + map.fVTOffset - 1);
423 } else {
424 // Not virtual, i.e. plain member func
425 return map.fPFN;
426 }
427 }
428
429 #else
430 #error Unknown architecture.
431 #endif /* __arm__ */
432
433 #endif /* !APPLE_KEXT_LEGACY_ABI */
434
435 /*!
436 * @define OSMemberFunctionCast
437 * @hidecontents
438 *
439 * @abstract
440 * Converts a C++ member function pointer, relative to an instance,
441 * to a C-style pointer to function.
442 *
443 * @param cptrtype The function type declaration to cast to
444 * (typically provided as a <code>typedef</code> by I/O KitKit classes).
445 * @param self The <code>this</code> pointer of the object whose function
446 * you wish to cache.
447 * @param func The pointer to the member function itself,
448 * something like <code>&Class::function</code>.
449 *
450 * @result
451 * A pointer to a function of the given type referencing <code>self</code>.
452 *
453 * @discussion
454 * This function is used to generate pointers to C++ functions for instances,
455 * such that they can be registered as callbacks with I/O Kit objects.
456 *
457 * No warnings are generated.
458 *
459 * This function will panic if an attempt is made to call it
460 * with a multiply-inheriting class.
461 */
462 #define OSMemberFunctionCast(cptrtype, self, func) \
463 (cptrtype) OSMetaClassBase:: \
464 _ptmf2ptf(self, (void (OSMetaClassBase::*)(void)) func)
465
466 protected:
467 OSMetaClassBase();
468 virtual ~OSMetaClassBase();
469
470 private:
471 // Disable copy constructors of OSMetaClassBase based objects
472 /* Not to be included in headerdoc.
473 *
474 * @function operator =
475 *
476 * @abstract
477 * Disable implicit copy constructor by making private
478 *
479 * @param src Reference to source object that isn't allowed to be copied.
480 */
481 void operator =(OSMetaClassBase &src);
482
483 /* Not to be included in headerdoc.
484 *
485 * @function OSMetaClassBase
486 *
487 * @abstract
488 * Disable implicit copy constructor by making private
489 *
490 * @param src Reference to source object that isn't allowed to be copied.
491 */
492 OSMetaClassBase(OSMetaClassBase &src);
493
494 public:
495
496 // xx-review: the original comment for this makes it sound to me like we don't
497 // xx-review: catch over-releasing an object...?
498
499 /*!
500 * @function release
501 *
502 * @abstract
503 * Abstract declaration of
504 * <code>@link
505 * //apple_ref/cpp/instm/OSObject/release/virtualvoid/(int)
506 * release(int freeWhen)@/link</code>.
507 *
508 * @discussion
509 * See
510 * <code>@link
511 * //apple_ref/cpp/instm/OSObject/release/virtualvoid/(int)
512 * release(int freeWhen)@/link</code>.
513 */
514 virtual void release(int freeWhen) const = 0;
515
516
517 /*!
518 * @function getRetainCount
519 *
520 * @abstract
521 * Abstract declaration of
522 * <code>@link
523 * //apple_ref/cpp/instm/OSObject/getRetainCount/virtualint/()
524 * getRetainCount()@/link</code>.
525 *
526 * @discussion
527 * See
528 * <code>@link
529 * //apple_ref/cpp/instm/OSObject/getRetainCount/virtualint/()
530 * OSObject::getRetainCount()@/link</code>.
531 */
532 virtual int getRetainCount() const = 0;
533
534
535 /*!
536 * @function retain
537 *
538 * @abstract
539 * Abstract declaration of
540 * <code>@link
541 * //apple_ref/cpp/instm/OSObject/retain/virtualvoid/()
542 * retain()@/link</code>.
543 *
544 * @discussion
545 * See
546 * <code>@link
547 * //apple_ref/cpp/instm/OSObject/retain/virtualvoid/()
548 * OSObject::retain()@/link</code>.
549 */
550 virtual void retain() const = 0;
551
552
553 /*!
554 * @function release
555 *
556 * @abstract
557 * Abstract declaration of
558 * <code>@link
559 * //apple_ref/cpp/instm/OSObject/release/virtualvoid/()
560 * release@/link</code>.
561 *
562 * @discussion
563 * See
564 * <code>@link
565 * //apple_ref/cpp/instm/OSObject/release/virtualvoid/()
566 * OSObject::release@/link</code>.
567 */
568 virtual void release() const = 0;
569
570
571 /*!
572 * @function serialize
573 *
574 * @abstract
575 * Abstract declaration of
576 * <code>@link
577 * //apple_ref/cpp/instm/OSObject/serialize/virtualbool/(OSSerialize*)
578 * serialize@/link</code>.
579 *
580 * @discussion
581 * See
582 * <code>@link
583 * //apple_ref/cpp/instm/OSObject/serialize/virtualbool/(OSSerialize*)
584 * OSObject::serialize@/link</code>.
585 */
586 virtual bool serialize(OSSerialize * serializer) const = 0;
587
588
589 /*!
590 * @function getMetaClass
591 *
592 * @abstract
593 * Returns the OSMetaClass representing
594 * an OSMetaClassBase subclass.
595 *
596 * @discussion
597 * OSObject overrides this abstract member function
598 * to return the OSMetaClass object that represents
599 * each class for run-time typing.
600 */
601 virtual const OSMetaClass * getMetaClass() const = 0;
602
603
604 /*!
605 * @function isEqualTo
606 *
607 * @abstract
608 * Checks whether another object is equal to the receiver.
609 *
610 * @param anObject The object to copmare to the receiver.
611 *
612 * @result
613 * <code>true</code> if the objects are equal, <code>false</code> otherwise.
614 *
615 * @discussion
616 * OSMetaClassBase implements this as a direct pointer comparison,
617 * since it has no other information to judge equality by.
618 * Subclasses generally override this function
619 * to do a more meaningful comparison.
620 * For example, OSString implements it to return
621 * <code>true</code> if <code>anObject</code>
622 * is derived from OSString and represents the same C string.
623 */
624 virtual bool isEqualTo(const OSMetaClassBase * anObject) const;
625
626
627 /*!
628 * @function metaCast
629 *
630 * @abstract
631 * Casts this object is to the class managed by the given OSMetaClass.
632 *
633 * @param toMeta A pointer to a constant OSMetaClass
634 * for the desired target type.
635 *
636 * @result
637 * <code>this</code> if the object is derived
638 * from the class managed by <code>toMeta</code>,
639 * otherwise <code>NULL</code>.
640 *
641 * @discussion
642 * It is far more convenient to use
643 * <code>@link OSDynamicCast OSDynamicCast@/link</code>.
644 */
645 OSMetaClassBase * metaCast(const OSMetaClass * toMeta) const;
646
647
648 /*!
649 * @function metaCast
650 *
651 * @abstract
652 * Casts this object is to the class managed by the named OSMetaClass.
653 *
654 * @param toMeta An OSSymbol naming the desired target type.
655 *
656 * @result
657 * <code>this</code> if the object is derived
658 * from the class named by <code>toMeta</code>,
659 * otherwise <code>NULL</code>.
660 *
661 * @discussion
662 * It is far more convenient to use
663 * <code>@link OSDynamicCast OSDynamicCast@/link</code>.
664 */
665 OSMetaClassBase * metaCast(const OSSymbol * toMeta) const;
666
667
668 /*!
669 * @function metaCast
670 *
671 * @abstract
672 * Casts this object is to the class managed by the named OSMetaClass.
673 *
674 * @param toMeta An OSString naming the desired target type.
675 * @result
676 * <code>this</code> if the object is derived
677 * from the class named by <code>toMeta</code>,
678 * otherwise <code>NULL</code>.
679 *
680 * @discussion
681 * It is far more convenient to use
682 * <code>@link OSDynamicCast OSDynamicCast@/link</code>.
683 */
684 OSMetaClassBase * metaCast(const OSString * toMeta) const;
685
686
687 /*!
688 * @function metaCast
689 *
690 * @abstract
691 * Casts this object is to the class managed by the named OSMetaClass.
692 *
693 * @param toMeta A C string naming the desired target type.
694 * @result
695 * <code>this</code> if the object is derived
696 * from the class named by <code>toMeta</code>,
697 * otherwise <code>NULL</code>.
698 *
699 * @discussion
700 * It is far more convenient to use
701 * <code>@link OSDynamicCast OSDynamicCast@/link</code>.
702 */
703 OSMetaClassBase * metaCast(const char * toMeta) const;
704
705 // Helper inlines for run-time type preprocessor macros
706 /*!
707 * @function safeMetaCast
708 *
709 * @abstract
710 * Casts an object is to the class managed by the given OSMetaClass.
711 *
712 * @param anObject A pointer to the object to be cast.
713 * @param toMeta A pointer to a constant OSMetaClass
714 * for the desired target type.
715 *
716 * @result
717 * <code>anObject</code> if the object is derived
718 * from the class managed by <code>toMeta</code>,
719 * otherwise <code>NULL</code>.
720 *
721 * @discussion
722 * It is far more convenient to use
723 * <code>@link OSDynamicCast OSDynamicCast@/link</code>.
724 */
725 static OSMetaClassBase * safeMetaCast(
726 const OSMetaClassBase * anObject,
727 const OSMetaClass * toMeta);
728
729 /*!
730 * @function checkTypeInst
731 *
732 * @abstract
733 * Checks whether an object instance is of the same class
734 * as another object instance (or a subclass of that class).
735 *
736 * @param inst A pointer to the object to check.
737 * @param typeinst A pointer to an object of the class being checked.
738 *
739 * @result
740 * <code>true</code> if the object is derived
741 * from the class of <code>typeinst</code>
742 * or a subclass of that class,
743 * otherwise <code>false</code>.
744 *
745 * @discussion
746 * It is far more convenient to use
747 * <code>@link OSCheckTypeInst OSCheckTypeInst@/link</code>.
748 */
749 static bool checkTypeInst(
750 const OSMetaClassBase * inst,
751 const OSMetaClassBase * typeinst);
752
753 static void initialize(void);
754
755 public:
756
757 /*!
758 * @function taggedRetain
759 *
760 * @abstract
761 * Abstract declaration of
762 * <code>@link
763 * //apple_ref/cpp/instm/OSObject/taggedRetain/virtualvoid/(constvoid*)
764 * taggedRetain(const void *)@/link</code>.
765 *
766 * @discussion
767 * See
768 * <code>@link
769 * //apple_ref/cpp/instm/OSObject/taggedRetain/virtualvoid/(constvoid*)
770 * OSObject::taggedRetain(const void *)@/link</code>.
771 */
772 // WAS: virtual void _RESERVEDOSMetaClassBase0();
773 virtual void taggedRetain(const void * tag = 0) const = 0;
774
775
776 /*!
777 * @function taggedRelease
778 *
779 * @abstract
780 * Abstract declaration of
781 * <code>@link
782 * //apple_ref/cpp/instm/OSObject/taggedRelease/virtualvoid/(constvoid*)
783 * taggedRelease(const void *)@/link</code>.
784 *
785 * @discussion
786 * See
787 * <code>@link
788 * //apple_ref/cpp/instm/OSObject/taggedRelease/virtualvoid/(constvoid*)
789 * OSObject::taggedRelease(const void *)@/link</code>.
790 */
791 // WAS: virtual void _RESERVEDOSMetaClassBase1();
792 virtual void taggedRelease(const void * tag = 0) const = 0;
793
794 protected:
795 /*!
796 * @function taggedRelease
797 *
798 * @abstract
799 * Abstract declaration of
800 * <code>@link
801 * //apple_ref/cpp/instm/OSObject/taggedRelease/virtualvoid/(constvoid*,constint)
802 * taggedRelease(const void *, const int freeWhen)@/link</code>.
803 *
804 * @discussion
805 * See
806 * <code>@link
807 * //apple_ref/cpp/instm/OSObject/taggedRelease/virtualvoid/(constvoid*,constint)
808 * OSObject::taggedRelease(const void *, const int freeWhen)@/link</code>.
809 */
810 // WAS: virtual void _RESERVEDOSMetaClassBase2();
811 virtual void taggedRelease(
812 const void * tag,
813 const int freeWhen) const = 0;
814
815 private:
816 #if APPLE_KEXT_VTABLE_PADDING
817 // Virtual Padding
818 virtual void _RESERVEDOSMetaClassBase3();
819 virtual void _RESERVEDOSMetaClassBase4();
820 virtual void _RESERVEDOSMetaClassBase5();
821 virtual void _RESERVEDOSMetaClassBase6();
822 virtual void _RESERVEDOSMetaClassBase7();
823 #endif
824 } APPLE_KEXT_COMPATIBILITY;
825
826
827 #ifdef XNU_KERNEL_PRIVATE
828 typedef bool (*OSMetaClassInstanceApplierFunction)(const OSObject * instance,
829 void * context);
830 #endif /* XNU_KERNEL_PRIVATE */
831
832 /*!
833 * @class OSMetaClass
834 *
835 * @abstract
836 * OSMetaClass manages run-time type information
837 * for Libkern and I/O Kit C++ classes.
838 *
839 * @discussion OSMetaClass manages run-time type information
840 * for Libkern and I/O Kit C++ classes.
841 * An instance of OSMetaClass exists for (nearly) every such C++ class,
842 * keeping track of inheritance relationships, class lookup by name,
843 * instance counts, and more.
844 * OSMetaClass operates almost entirely behind the scenes,
845 * and kernel extensions should rarely, if ever,
846 * have to interact directly with OSMetaClass.
847 *
848 * <b>Use by Kernel Extensions</b>
849 *
850 * While kernel extensions rarey interact directly with OSMetaClass at run time,
851 * they must register their classes with the metaclass system
852 * using the macros declared here.
853 * The class declaration should use one of these two macros
854 * before its first member function declaration:
855 * <ul>
856 * <li><code>@link OSDeclareDefaultStructors OSDeclareDefaultStructors@/link</code> -
857 * for classes with no abstract member function declarations</li>
858 * <li><code>@link OSDeclareAbstractStructors OSDeclareAbstractStructors@/link</code> -
859 * for classes with at least one abstract member function declaration</li>
860 * <li><code>@link OSDeclareFinalStructors OSDeclareFinalStructors@/link</code> -
861 * for classes that should not be subclassable by another kext</li>
862 * </ul>
863 *
864 * The class implementation should then use one of these macros:
865 * <ul>
866 * <li><code>@link OSDefineMetaClassAndStructors
867 * OSDefineMetaClassAndStructors@/link</code> -
868 * for classes with no abstract member function declarations</li>
869 * <li><code>@link OSDefineMetaClassAndAbstractStructors
870 * OSDefineMetaClassAndAbstractStructors@/link</code> -
871 * for classes with at least one abstract member function declaration</li>
872 * <li><code>@link OSDefineMetaClassAndFinalStructors
873 * OSDefineMetaClassAndFinalStructors@/link</code> -
874 * for classes that should not be subclassable by another kext</li>
875 * </ul>
876 *
877 * Classes in kernel extensions that are intended for use as libraries
878 * may need to reserve vtable slots to preserve binary compatibility
879 * as new functions are added. They may do so with these macros:
880 * <ul>
881 * <li><code>@link OSMetaClassDeclareReservedUnused
882 * OSMetaClassDeclareReservedUnused@/link</code> -
883 * reserves a vtable slot</li>
884 * <li><code>@link OSMetaClassDefineReservedUnused
885 * OSMetaClassDefineReservedUnused@/link</code> -
886 * defines the reserved vtable slot as an unimplemented function</li>
887 * <li><code>@link OSMetaClassDeclareReservedUsed
888 * OSMetaClassDeclareReservedUsed@/link</code> -
889 * documents that a formerly reserved slot is now used</li>
890 * <li><code>@link OSMetaClassDefineReservedUsed
891 * OSMetaClassDefineReservedUsed@/link</code> -
892 * documents that a formerly reserved slot is now used</li>
893 * </ul>
894 *
895 * <b>Use Restrictions</b>
896 *
897 * OSMetaClass should not be explicitly subclassed by kernel extensions
898 * (the declare/define macros do that),
899 * nor should kernel extensions call its run-time type functions directly.
900 *
901 * OSMetaClass functions should be considered
902 * <b>unsafe</b> to call in a primary interrupt context.
903 *
904 * <b>Concurrency Protection</b>
905 *
906 * Kernel extensions should in general not interact
907 * with OSMetaClass objects directly,
908 * instead using the run-time type macros.
909 * Much of OSMetaClass's interface is intended for use
910 * by the run-time type information system,
911 * which handles concurrency and locking internally.
912 */
913 class OSMetaClass : private OSMetaClassBase
914 {
915 friend class OSKext;
916 #if IOKITSTATS
917 friend class IOStatistics;
918 #endif
919
920 private:
921 // Can never be allocated must be created at compile time
922 static void * operator new(size_t size);
923
924 /* Reserved for future use. (Internal use only) */
925 struct ExpansionData *reserved;
926
927 /* superClass Handle to the superclass's meta class. */
928 const OSMetaClass *superClassLink;
929
930 /* className OSSymbol of the class' name. */
931 const OSSymbol *className;
932
933 /* classSize How big is a single instance of this class. */
934 unsigned int classSize;
935
936 /* instanceCount Roughly number of instances of the object,
937 * +1 for each direct subclass with a nonzero refcount.
938 * Used primarily as a code-in-use flag.
939 */
940 mutable unsigned int instanceCount;
941
942 /* Not to be included in headerdoc.
943 *
944 * @function OSMetaClass
945 *
946 * @abstract
947 * The default private constructor.
948 */
949 OSMetaClass();
950
951 // Called by postModLoad
952 /* Not to be included in headerdoc.
953 *
954 * @function logError
955 *
956 * @abstract
957 * Logs an error string for an <code>OSReturn</code> value
958 * using <code>printf</code>.
959 *
960 * @param result The <code>OSReturn</code> value for which to log a message.
961 *
962 * @discussion
963 * This function is used to log errors loading kernel extensions.
964 * Kernel extensions themselves should not call it.
965 */
966 static void logError(OSReturn result);
967
968 public:
969
970 /*!
971 * @function getMetaClassWithName
972 *
973 * @abstract
974 * Look up a metaclass in the run-time type information system.
975 *
976 * @param name The name of the desired class's metaclass.
977 *
978 * @result
979 * A pointer to the metaclass object if found, <code>NULL</code> otherwise.
980 */
981 static const OSMetaClass * getMetaClassWithName(const OSSymbol * name);
982
983 #if XNU_KERNEL_PRIVATE
984
985 /*!
986 * @function copyMetaClassWithName
987 *
988 * @abstract
989 * Look up a metaclass in the run-time type information system.
990 *
991 * @param name The name of the desired class's metaclass.
992 *
993 * @result
994 * A pointer to the metaclass object if found, <code>NULL</code> otherwise.
995 * The metaclass will be protected from unloading until releaseMetaClass()
996 * is called.
997 */
998 static const OSMetaClass * copyMetaClassWithName(const OSSymbol * name);
999 /*!
1000 * @function releaseMetaClass
1001 *
1002 * @abstract
1003 * Releases reference obtained from copyMetaClassWithName().
1004 *
1005 * @discussion
1006 * The metaclass will be protected from unloading until releaseMetaClass()
1007 * is called.
1008 */
1009 void releaseMetaClass() const;
1010
1011 #endif /* XNU_KERNEL_PRIVATE */
1012
1013 protected:
1014 /*!
1015 * @function retain
1016 *
1017 * @abstract
1018 * Implements the abstract <code>retain</code> function to do nothing.
1019 *
1020 * @discussion
1021 * Since an OSMetaClass instance must remain in existence
1022 * for as long as its kernel extension is loaded,
1023 * OSMetaClass does not use reference-counting.
1024 */
1025 virtual void retain() const;
1026
1027
1028 /*!
1029 * @function release
1030 *
1031 * @abstract
1032 * Implements the abstract <code>release</code> function to do nothing.
1033 *
1034 * @discussion
1035 * Since an OSMetaClass instance must remain in existence
1036 * for as long as its kernel extension is loaded,
1037 * OSMetaClass does not use reference-counting.
1038 */
1039 virtual void release() const;
1040
1041
1042 /*!
1043 * @function release
1044 *
1045 * @abstract
1046 * Implements the abstract <code>release(int freeWhen)</code>
1047 * function to do nothing.
1048 *
1049 * @param freeWhen Unused.
1050 *
1051 * @discussion
1052 * Since an OSMetaClass instance must remain in existence
1053 * for as long as its kernel extension is loaded,
1054 * OSMetaClass does not use reference-counting.
1055 */
1056 virtual void release(int freeWhen) const;
1057
1058
1059 /*!
1060 * @function taggedRetain
1061 *
1062 * @abstract
1063 * Implements the abstract <code>taggedRetain(const void *)</code>
1064 * function to do nothing.
1065 *
1066 * @param tag Unused.
1067 *
1068 * @discussion
1069 * Since an OSMetaClass instance must remain in existence
1070 * for as long as its kernel extension is loaded,
1071 * OSMetaClass does not use reference-counting.
1072 */
1073 virtual void taggedRetain(const void * tag = 0) const;
1074
1075
1076 /*!
1077 * @function taggedRelease
1078 *
1079 * @abstract
1080 * Implements the abstract <code>taggedRelease(const void *)</code>
1081 * function to do nothing.
1082 *
1083 * @param tag Unused.
1084 *
1085 * @discussion
1086 * Since an OSMetaClass instance must remain in existence
1087 * for as long as its kernel extension is loaded,
1088 * OSMetaClass does not use reference-counting.
1089 */
1090 virtual void taggedRelease(const void * tag = 0) const;
1091
1092
1093 /*!
1094 * @function taggedRelease
1095 *
1096 * @abstract
1097 * Implements the abstract <code>taggedRelease(const void *, cont int)</code>
1098 * function to do nothing.
1099 *
1100 * @param tag Unused.
1101 * @param freeWhen Unused.
1102 *
1103 * @discussion
1104 * Since an OSMetaClass instance must remain in existence
1105 * for as long as its kernel extension is loaded,
1106 * OSMetaClass does not use reference-counting.
1107 */
1108 virtual void taggedRelease(
1109 const void * tag,
1110 const int freeWhen) const;
1111
1112
1113 /*!
1114 * @function getRetainCount
1115 *
1116 * @abstract
1117 * Implements the abstract <code>getRetainCount</code>
1118 * function to return 0.
1119 *
1120 * @result
1121 * Always returns 0.
1122 *
1123 * @discussion
1124 * Since an OSMetaClass instance must remain in existence
1125 * for as long as its kernel extension is loaded,
1126 * OSMetaClass does not use reference-counting.
1127 */
1128 virtual int getRetainCount() const;
1129
1130
1131 /* Not to be included in headerdoc.
1132 *
1133 * @function getMetaClass
1134 *
1135 * @abstract
1136 * Returns the meta-metaclass.
1137 *
1138 * @result
1139 * The metaclass of the OSMetaClass object.
1140 */
1141 virtual const OSMetaClass * getMetaClass() const;
1142
1143
1144 /*!
1145 * @function OSMetaClass
1146 *
1147 * @abstract
1148 * Constructor for OSMetaClass objects.
1149 *
1150 * @param className A C string naming the C++ class
1151 * that this OSMetaClass represents.
1152 * @param superclass The OSMetaClass object representing the superclass
1153 * of this metaclass's class.
1154 * @param classSize The allocation size of the represented C++ class.
1155 *
1156 * @discussion
1157 * This constructor is protected and cannot be used
1158 * to instantiate OSMetaClass directly, as OSMetaClass is an abstract class.
1159 * This function is called during kext loading
1160 * to queue C++ classes for registration.
1161 * See <code>@link preModLoad preModLoad@/link</code> and
1162 * <code>@link postModLoad postModLoad@/link</code>.
1163 */
1164 OSMetaClass(const char * className,
1165 const OSMetaClass * superclass,
1166 unsigned int classSize);
1167
1168
1169 /*!
1170 * @function ~OSMetaClass
1171 *
1172 * @abstract
1173 * Destructor for OSMetaClass objects.
1174 *
1175 * @discussion
1176 * This function is called when the kernel extension that implements
1177 * the metaclass's class is unloaded.
1178 * The destructor removes all references to the class
1179 * from the run-time type information system.
1180 */
1181 virtual ~OSMetaClass();
1182
1183 // Needs to be overriden as NULL as all OSMetaClass objects are allocated
1184 // statically at compile time, don't accidently try to free them.
1185 void operator delete(void *, size_t) { }
1186
1187 public:
1188 static const OSMetaClass * const metaClass;
1189
1190 /*!
1191 * @function preModLoad
1192 *
1193 * @abstract
1194 * Prepares the run-time type system
1195 * for the creation of new metaclasses
1196 * during loading of a kernel extension (module).
1197 *
1198 * @param kextID The bundle ID of the kext being loaded.
1199 *
1200 * @result
1201 * An opaque handle to the load context
1202 * for the kernel extension on success;
1203 * <code>NULL</code> on failure.
1204 *
1205 * @discussion
1206 * <i>Not for use by kernel extensions.</i>
1207 *
1208 * Prepares the run-time type information system to record and register
1209 * metaclasses created by static constructors until a subsequent call to
1210 * <code>@link postModLoad postModLoad@/link</code>.
1211 * <code>preModLoad</code> takes a lock to ensure processing of a single
1212 * load operation at a time; the lock is released by
1213 * <code>@link postModLoad postModLoad@/link</code>.
1214 * Any OSMetaClass constructed between these two function calls
1215 * will be associated with <code>kextID</code>.
1216 */
1217 static void * preModLoad(const char * kextID);
1218
1219
1220 /*!
1221 * @function checkModLoad
1222 *
1223 * @abstract
1224 * Checks whether the current kext load operation can proceed.
1225 *
1226 * @param loadHandle The opaque handle returned
1227 * by <code>@link preModLoad preModLoad@/link</code>.
1228 * @result
1229 * <code>true</code> if no errors are outstanding
1230 * and the system is ready to process more metaclasses.
1231 *
1232 * @discussion
1233 * <i>Not for use by kernel extensions.</i>
1234 */
1235 static bool checkModLoad(void * loadHandle);
1236
1237
1238 /*!
1239 * @function postModLoad
1240 *
1241 * @abstract
1242 * Registers the metaclasses created during loading of a kernel extension.
1243 *
1244 * @param loadHandle The opaque handle returned
1245 * by <code>@link preModLoad preModLoad@/link</code>.
1246 * @result
1247 * The error code of the first error encountered,
1248 * or
1249 * <code>@link
1250 * //apple_ref/cpp/macro/kOSReturnSuccess
1251 * kOSReturnSuccess@/link</code>
1252 * if no error occurred.
1253 *
1254 * @discussion
1255 * <i>Not for use by kernel extensions.</i>
1256 *
1257 * Called after all static constructors in a kernel extension
1258 * have created metaclasses,
1259 * this function checks for duplicate class names,
1260 * then registers the new metaclasses under the kext ID
1261 * that @link preModLoad preModLoad@/link was called with,
1262 * so that they can be dynamically allocated
1263 * and have their instance counts tracked.
1264 * <code>postModLoad</code> releases the lock taken by
1265 * <code>@link preModLoad preModLoad@/link</code>.
1266 */
1267 static OSReturn postModLoad(void * loadHandle);
1268
1269 /*!
1270 * @function modHasInstance
1271 *
1272 * @abstract
1273 * Returns whether any classes defined by the named
1274 * kernel extension (or their subclasses) have existing instances.
1275 *
1276 * @param kextID The bundle ID of the kernel extension to check.
1277 *
1278 * @result
1279 * <code>true</code> if the kext is found and
1280 * if any class defined by that kext
1281 * has a nonzero instance count,
1282 * <code>false</code> otherwise.
1283 *
1284 * @discussion
1285 * This function is called before a kernel extension's static destructors
1286 * are invoked, prior to unloading the extension.
1287 * If any classes stil have instances or subclasses with instances,
1288 * those classes are logged
1289 * (using <code>@link reportModInstances reportModInstances@/link</code>) and
1290 * the kernel extension is not be unloaded.
1291 */
1292 static bool modHasInstance(const char * kextID);
1293
1294
1295 /*!
1296 * @function reportModInstances
1297 *
1298 * @abstract
1299 * Logs the instance counts for classes
1300 * defined by a kernel extension.
1301 *
1302 * @param kextID The bundle ID of the kernel extension to report on.
1303 *
1304 * @discussion
1305 * This function prints the names and instance counts
1306 * of any class defined by <code>kextID</code>
1307 * that has a nonzero instance count.
1308 * It's called by <code>@link modHasInstance modHasInstance@/link</code>
1309 * to help diagnose problems unloading kernel extensions.
1310 */
1311 static void reportModInstances(const char * kextID);
1312
1313
1314 /*!
1315 * @function considerUnloads
1316 *
1317 * @abstract
1318 * Schedule automatic unloading of unused kernel extensions.
1319 *
1320 * @discussion
1321 * This function schedules a check for kernel extensions
1322 * that can be automatically unloaded,
1323 * canceling any currently scheduled check.
1324 * At that time, any such kexts with no Libkern C++ instances
1325 * and no external references are unloaded.
1326 *
1327 * The I/O Kit calls this function when matching goes idle.
1328 *
1329 * Kernel extensions that define subclasses of
1330 * @link //apple_ref/doc/class/IOService IOService@/link
1331 * are eligible for automatic unloading.
1332 *
1333 * (On releases of Mac OS X prior to Snow Leopard (10.6),
1334 * any kernel extension defining any Libkern C++ class
1335 * was eligible for automatic unloading,
1336 * but that unload did not call the module stop routine.
1337 * Non-I/O Kit kernel extensions that define Libkern C++ subclasses
1338 * should be sure to have OSBundleLibraries declarations that ensure
1339 * they will not load on releases prior to Snow Leopard.)
1340 */
1341 static void considerUnloads();
1342
1343 #if XNU_KERNEL_PRIVATE
1344 static bool removeClasses(OSCollection * metaClasses);
1345 #endif /* XNU_KERNEL_PRIVATE */
1346
1347 /*!
1348 * @function allocClassWithName
1349 *
1350 * @abstract
1351 * Allocates an instance of a named OSObject-derived class.
1352 *
1353 * @param name The name of the desired class.
1354 *
1355 * @result
1356 * A pointer to the newly-allocated, uninitialized object on success;
1357 * <code>NULL</code> on failure.
1358 *
1359 * @discussion
1360 * Kernel extensions should not need to use this function
1361 * directly, instead using static instance-creation functions
1362 * defined by classes.
1363 *
1364 * This function consults the run-time type information system
1365 * to find the metaclass for the named class.
1366 * If it exists, it calls the metaclass's <code>@link alloc alloc@/link</code>
1367 * function and returns the result.
1368 */
1369 static OSObject * allocClassWithName(const OSSymbol * name);
1370
1371
1372 /*!
1373 * function allocClassWithName
1374 *
1375 * @abstract
1376 * Allocates an instance of a named OSObject-derived class.
1377 *
1378 * @param name The name of the desired class.
1379 *
1380 * @result
1381 * A pointer to the newly-allocated, uninitialized object on success;
1382 * <code>NULL</code> on failure.
1383 *
1384 * @discussion
1385 * Kernel extensions should not need to use this function
1386 * directly, instead using static instance-creation functions
1387 * defined by classes.
1388 *
1389 * This function consults the run-time type information system
1390 * to find the metaclass for the named class.
1391 * If it exists, it calls the metaclass's <code>@link alloc alloc@/link</code>
1392 * function and returns the result.
1393 */
1394 static OSObject * allocClassWithName(const OSString * name);
1395
1396
1397 /*!
1398 * function allocClassWithName
1399 *
1400 * @abstract
1401 * Allocates an instance of a named OSObject-derived class.
1402 *
1403 * @param name The name of the desired class.
1404 *
1405 * @result
1406 * A pointer to the newly-allocated, uninitialized object on success;
1407 * <code>NULL</code> on failure.
1408 *
1409 * @discussion
1410 * Kernel extensions should not need to use this function
1411 * directly, instead using static instance-creation functions
1412 * defined by classes.
1413 *
1414 * This function consults the run-time type information system
1415 * to find the metaclass for the named class.
1416 * If it exists, it calls the metaclass's <code>@link alloc alloc@/link</code>
1417 * function and returns the result.
1418 */
1419 static OSObject * allocClassWithName(const char * name);
1420
1421
1422 /*!
1423 * @function checkMetaCastWithName
1424 *
1425 * @abstract
1426 * Search the metaclass inheritance hierarchy by name for an object instance.
1427 *
1428 * @param className The name of the desired class or superclass.
1429 * @param object The object whose metaclass begins the search.
1430 *
1431 * @result
1432 * <code>object</code> if it's derived from <code>className</code>;
1433 * <code>NULL</code> otherwise.
1434 *
1435 * @discussion
1436 * This function is the basis of the Libkern run-time type-checking system.
1437 * Kernel extensions should not use it directly,
1438 * instead using <code>@link OSDynamicCast OSDynamicCast@/link</code> or
1439 * <code>@link OSCheckTypeInst OSCheckTypeInst@/link</code>.
1440 */
1441 static OSMetaClassBase * checkMetaCastWithName(
1442 const OSSymbol * className,
1443 const OSMetaClassBase * object);
1444
1445 /*!
1446 * @function checkMetaCastWithName
1447 *
1448 * @abstract
1449 * Search the metaclass inheritance hierarchy by name for an object instance.
1450 *
1451 * @param className The name of the desired class or superclass.
1452 * @param object The object whose metaclass begins the search.
1453 *
1454 * @result
1455 * <code>object</code> if it's derived from <code>className</code>;
1456 * <code>NULL</code> otherwise.
1457 *
1458 * @discussion
1459 * Kernel extensions should not use this function directly,
1460 * instead using <code>@link OSDynamicCast OSDynamicCast@/link</code> or
1461 * <code>@link OSCheckTypeInst OSCheckTypeInst@/link</code>.
1462 */
1463 static OSMetaClassBase * checkMetaCastWithName(
1464 const OSString * className,
1465 const OSMetaClassBase * object);
1466
1467 /*!
1468 * @function checkMetaCastWithName
1469 *
1470 * @abstract
1471 * Search the metaclass inheritance hierarchy by name for an object instance.
1472 *
1473 * @param className The name of the desired class or superclass.
1474 * @param object The object whose metaclass begins the search.
1475 *
1476 * @result
1477 * <code>object</code> if it's derived from <code>className</code>;
1478 * <code>NULL</code> otherwise.
1479 *
1480 * @discussion
1481 * Kernel extensions should not use this function directly,
1482 * instead using <code>@link OSDynamicCast OSDynamicCast@/link</code> or
1483 * <code>@link OSCheckTypeInst OSCheckTypeInst@/link</code>.
1484 */
1485 static OSMetaClassBase * checkMetaCastWithName(
1486 const char * className,
1487 const OSMetaClassBase * object);
1488
1489
1490 /*!
1491 * @function instanceConstructed
1492 *
1493 * @abstract
1494 * Counts the instances of the class managed by this metaclass.
1495 *
1496 * @discussion
1497 * <i>Not for use by kernel extensions.</i>
1498 *
1499 * Every non-abstract class that inherits from OSObject
1500 * has a default constructor that calls it's own metaclass's
1501 * <code>instanceConstructed</code> function.
1502 * This constructor is defined by the
1503 * <code>@link
1504 * OSDefineMetaClassAndStructors
1505 * OSDefineMetaClassAndStructors@/link</code>
1506 * macro that all OSObject subclasses must use.
1507 *
1508 * If a class's instance count goes from 0 to 1--that is,
1509 * upon the creation of the first instance of that class--the
1510 * superclass's instance count is also incremented.
1511 * This propagates reference counts up the inheritance chain so that
1512 * superclasses are counted as "in use" when subclasses have instances.
1513 */
1514 void instanceConstructed() const;
1515
1516
1517 /*!
1518 * @function instanceDestructed
1519 *
1520 * @abstract
1521 * Counts the instances of the class managed by this metaclass.
1522 *
1523 * @discussion
1524 * Every non-abstract class that inherits from OSObject
1525 * has a default destructor that calls it's own metaclass's
1526 * <code>instanceDestructed</code> function.
1527 * This constructor is defined by the
1528 * @link OSDefineMetaClassAndStructors OSDefineMetaClassAndStructors@/link
1529 * macro that all OSObject subclasses must use.
1530 *
1531 * If a class's instance count goes from 1 to 0--that is,
1532 * upon the destruction of the last instance of that class--the
1533 * superclass's instance count is also decremented.
1534 * This reduces "in use" counts from superclasses when their subclasses
1535 * no longer have instances.
1536 */
1537 void instanceDestructed() const;
1538
1539
1540 /*!
1541 * @function checkMetaCast
1542 *
1543 * @abstract
1544 * Check whether a given object is an instance of the receiving
1545 * metaclass's class or one derived from it.
1546 *
1547 * @param object The object to check for inheritance.
1548 *
1549 * @result
1550 * <code>object</code> if it is derived from the receiver's class,
1551 * <code>NULL</code> if not.
1552 */
1553 OSMetaClassBase * checkMetaCast(const OSMetaClassBase * object) const;
1554
1555
1556 /*!
1557 * @function getInstanceCount
1558 *
1559 * @abstract
1560 * Returns the number of existing instances of the metaclass's class.
1561 *
1562 * @result
1563 * The number of existing instances of the metaclass's class,
1564 * plus 1 for each subclass with any instance.
1565 */
1566 unsigned int getInstanceCount() const;
1567
1568
1569 /*!
1570 * @function getSuperClass
1571 *
1572 * @abstract
1573 * Returns the super-metaclass of the receiver.
1574 *
1575 * @result
1576 * Returns a pointer to the super-metaclass of the receiving
1577 * OSMetaClass, or <code>NULL</code> for OSObject's metaclass.
1578 */
1579 const OSMetaClass * getSuperClass() const;
1580
1581 /*!
1582 * @function getKmodName
1583 *
1584 * @abstract
1585 * Returns the bundle identifier of the kernel extension
1586 * that defines this metaclass.
1587 *
1588 * @result
1589 * The bundle identifier of the kernel extension that defines this metaclass.
1590 *
1591 * @discussion
1592 * "Kmod" is an older term for kernel extension.
1593 */
1594 const OSSymbol * getKmodName() const;
1595
1596
1597 /*!
1598 * @function getClassName
1599 *
1600 * @abstract
1601 * Returns the name of the C++ class managed by this metaclass.
1602 *
1603 * @result
1604 * Returns the name of the C++ class managed by this metaclass.
1605 */
1606 const char * getClassName() const;
1607 const OSSymbol * getClassNameSymbol() const;
1608
1609
1610 /*!
1611 * @function getClassSize
1612 *
1613 * @abstract
1614 * Returns the allocation size of the C++ class managed by this metaclass.
1615 *
1616 * @result
1617 * The allocation size of the C++ class managed by this metaclass.
1618 */
1619 unsigned int getClassSize() const;
1620
1621
1622 /*!
1623 * @function alloc
1624 *
1625 * @abstract
1626 * Allocates an instance of the C++ class managed by this metaclass.
1627 *
1628 * @result
1629 * A pointer to the newly allocated, uninitialized instance,
1630 * with a retain count of 1; <code>NULL</code> on allocation failure.
1631 *
1632 * @discussion
1633 * This function is automatically created by the metaclass-registration macros
1634 * to enable dynamic instance allocation.
1635 */
1636 virtual OSObject * alloc() const = 0;
1637
1638 #ifdef XNU_KERNEL_PRIVATE
1639 void addInstance(const OSObject * instance, bool super = false) const;
1640 void removeInstance(const OSObject * instance, bool super = false) const;
1641 void applyToInstances(OSMetaClassInstanceApplierFunction applier,
1642 void * context) const;
1643 static void applyToInstancesOfClassName(
1644 const OSSymbol * name,
1645 OSMetaClassInstanceApplierFunction applier,
1646 void * context);
1647 private:
1648 static void applyToInstances(OSOrderedSet * set,
1649 OSMetaClassInstanceApplierFunction applier,
1650 void * context);
1651 public:
1652 #endif /* XNU_KERNEL_PRIVATE */
1653
1654 /* Not to be included in headerdoc.
1655 *
1656 * @define OSDeclareCommonStructors
1657 * @hidecontents
1658 *
1659 * @abstract
1660 * Helper macro for for the standard metaclass-registration macros.
1661 * DO NOT USE.
1662 *
1663 * @param className The name of the C++ class, as a raw token,
1664 * <i>not</i> a string or macro.
1665 */
1666 #define OSDeclareCommonStructors(className) \
1667 private: \
1668 static const OSMetaClass * const superClass; \
1669 public: \
1670 static const OSMetaClass * const metaClass; \
1671 static class MetaClass : public OSMetaClass { \
1672 public: \
1673 MetaClass(); \
1674 virtual OSObject *alloc() const; \
1675 } gMetaClass; \
1676 friend class className ::MetaClass; \
1677 virtual const OSMetaClass * getMetaClass() const APPLE_KEXT_OVERRIDE; \
1678 protected: \
1679 className (const OSMetaClass *); \
1680 virtual ~ className ()
1681
1682
1683 /*!
1684 * @define OSDeclareDefaultStructors
1685 * @hidecontents
1686 *
1687 * @abstract
1688 * Declares run-time type information and functions
1689 * for a concrete Libkern C++ class.
1690 *
1691 * @param className The name of the C++ class, as a raw token,
1692 * <i>not</i> a string or macro.
1693 *
1694 * @discussion
1695 * Concrete Libkern C++ classes should "call" this macro
1696 * immediately after the opening brace in a class declaration.
1697 * It leaves the current privacy state as <code>protected:</code>.
1698 */
1699 #define OSDeclareDefaultStructors(className) \
1700 OSDeclareCommonStructors(className); \
1701 public: \
1702 className (); \
1703 protected:
1704
1705
1706 /*!
1707 * @define OSDeclareAbstractStructors
1708 * @hidecontents
1709 *
1710 * @abstract
1711 * Declares run-time type information and functions
1712 * for an abstract Libkern C++ class.
1713 *
1714 * @param className The name of the C++ class, as a raw token,
1715 * <i>not</i> a string or macro.
1716 *
1717 * @discussion
1718 * Abstract Libkern C++ classes--those with at least one
1719 * pure virtual method--should "call" this macro
1720 * immediately after the opening brace in a class declaration.
1721 * It leaves the current privacy state as <code>protected:</code>.
1722 */
1723 #define OSDeclareAbstractStructors(className) \
1724 OSDeclareCommonStructors(className); \
1725 private: \
1726 className (); /* Make primary constructor private in abstract */ \
1727 protected:
1728
1729 /*!
1730 * @define OSDeclareFinalStructors
1731 * @hidecontents
1732 *
1733 * @abstract
1734 * Declares run-time type information and functions
1735 * for a final (non-subclassable) Libkern C++ class.
1736 *
1737 * @param className The name of the C++ class, as a raw token,
1738 * <i>not</i> a string or macro.
1739 *
1740 * @discussion
1741 * Final Libkern C++ classes--those that do not allow subclassing--should
1742 * "call" this macro immediately after the opening brace in a class declaration.
1743 * (Final classes in the kernel may actually have subclasses in the kernel,
1744 * but kexts cannot define any subclasses of a final class.)
1745 * It leaves the current privacy state as <code>protected:</code>.
1746 *
1747 * <b>Note:</b> If the class is exported by a pseudokext (symbol set),
1748 * the final symbol generated by this macro must be exported
1749 * for the final-class attribute to be enforced.
1750 *
1751 * <b>Warning:</b> Changing a class from "Default" to "Final" will break
1752 * binary compatibility.
1753 */
1754 #define OSDeclareFinalStructors(className) \
1755 OSDeclareDefaultStructors(className) \
1756 private: \
1757 void __OSFinalClass(void); \
1758 protected:
1759
1760
1761 /* Not to be included in headerdoc.
1762 *
1763 * @define OSDefineMetaClassWithInit
1764 * @hidecontents
1765 *
1766 * @abstract
1767 * Helper macro for for the standard metaclass-registration macros.
1768 * DO NOT USE.
1769 *
1770 * @param className The name of the C++ class, as a raw token,
1771 * <i>not</i> a string or macro.
1772 * @param superclassName The name of the superclass of the C++ class,
1773 * as a raw token,
1774 * <i>not</i> a string or macro.
1775 * @param init A function to call in the constructor
1776 * of the class's OSMetaClass.
1777 */
1778 #define OSDefineMetaClassWithInit(className, superclassName, init) \
1779 /* Class global data */ \
1780 className ::MetaClass className ::gMetaClass; \
1781 const OSMetaClass * const className ::metaClass = \
1782 & className ::gMetaClass; \
1783 const OSMetaClass * const className ::superClass = \
1784 & superclassName ::gMetaClass; \
1785 /* Class member functions */ \
1786 className :: className(const OSMetaClass *meta) \
1787 : superclassName (meta) { } \
1788 className ::~ className() { } \
1789 const OSMetaClass * className ::getMetaClass() const \
1790 { return &gMetaClass; } \
1791 /* The ::MetaClass constructor */ \
1792 className ::MetaClass::MetaClass() \
1793 : OSMetaClass(#className, className::superClass, sizeof(className)) \
1794 { init; }
1795
1796
1797 /* Not to be included in headerdoc.
1798 *
1799 * @define OSDefineAbstractStructors
1800 * @hidecontents
1801 *
1802 * @abstract
1803 * Helper macro for for the standard metaclass-registration macros.
1804 * DO NOT USE.
1805 *
1806 * @param className The name of the C++ class, as a raw token,
1807 * <i>not</i> a string or macro.
1808 * @param superclassName The name of the superclass of the C++ class,
1809 * as a raw token,
1810 * <i>not</i> a string or macro.
1811 */
1812 #define OSDefineAbstractStructors(className, superclassName) \
1813 OSObject * className ::MetaClass::alloc() const { return 0; }
1814
1815
1816 /* Not to be included in headerdoc.
1817 *
1818 * @define OSDefineDefaultStructors
1819 * @hidecontents
1820 *
1821 * @abstract
1822 * Helper macro for for the standard metaclass-registration macros.
1823 * DO NOT USE.
1824 *
1825 * @param className The name of the C++ class, as a raw token,
1826 * <i>not</i> a string or macro.
1827 * @param superclassName The name of the superclass of the C++ class,
1828 * as a raw token,
1829 * <i>not</i> a string or macro.
1830 */
1831 #define OSDefineDefaultStructors(className, superclassName) \
1832 OSObject * className ::MetaClass::alloc() const \
1833 { return new className; } \
1834 className :: className () : superclassName (&gMetaClass) \
1835 { gMetaClass.instanceConstructed(); }
1836
1837 /* Not to be included in headerdoc.
1838 *
1839 * @define OSDefineDefaultStructors
1840 * @hidecontents
1841 *
1842 * @abstract
1843 * Helper macro for for the standard metaclass-registration macros.
1844 * DO NOT USE.
1845 *
1846 * @param className The name of the C++ class, as a raw token,
1847 * <i>not</i> a string or macro.
1848 * @param superclassName The name of the superclass of the C++ class,
1849 * as a raw token,
1850 * <i>not</i> a string or macro.
1851 */
1852 #define OSDefineFinalStructors(className, superclassName) \
1853 OSDefineDefaultStructors(className, superclassName) \
1854 void className ::__OSFinalClass(void) { }
1855
1856
1857 /* Not to be included in headerdoc.
1858 *
1859 * @define OSDefineMetaClassAndStructorsWithInit
1860 * @hidecontents
1861 *
1862 * @abstract
1863 * Helper macro for for the standard metaclass-registration macros.
1864 * DO NOT USE.
1865 *
1866 * @param className The name of the C++ class, as a raw token,
1867 * <i>not</i> a string or macro.
1868 * @param superclassName The name of the superclass of the C++ class,
1869 * as a raw token,
1870 * <i>not</i> a string or macro.
1871 * @param init A function to call in the constructor
1872 * of the class's OSMetaClass.
1873 */
1874 #define OSDefineMetaClassAndStructorsWithInit(className, superclassName, init) \
1875 OSDefineMetaClassWithInit(className, superclassName, init) \
1876 OSDefineDefaultStructors(className, superclassName)
1877
1878
1879 /* Not to be included in headerdoc.
1880 *
1881 * @define OSDefineMetaClassAndAbstractStructorsWithInit
1882 * @hidecontents
1883 *
1884 * @abstract
1885 * Helper macro for for the standard metaclass-registration macros.
1886 * DO NOT USE.
1887 *
1888 * @param className The name of the C++ class, as a raw token,
1889 * <i>not</i> a string or macro.
1890 * @param superclassName The name of the superclass of the C++ class,
1891 * as a raw token,
1892 * <i>not</i> a string or macro.
1893 * @param init A function to call in the constructor
1894 * of the class's OSMetaClass.
1895 */
1896 #define OSDefineMetaClassAndAbstractStructorsWithInit(className, superclassName, init) \
1897 OSDefineMetaClassWithInit(className, superclassName, init) \
1898 OSDefineAbstractStructors(className, superclassName)
1899
1900
1901 /* Not to be included in headerdoc.
1902 *
1903 * @define OSDefineMetaClassAndFinalStructorsWithInit
1904 * @hidecontents
1905 *
1906 * @abstract
1907 * Helper macro for for the standard metaclass-registration macros.
1908 * DO NOT USE.
1909 *
1910 * @param className The name of the C++ class, as a raw token,
1911 * <i>not</i> a string or macro.
1912 * @param superclassName The name of the superclass of the C++ class,
1913 * as a raw token,
1914 * <i>not</i> a string or macro.
1915 * @param init A function to call in the constructor
1916 * of the class's OSMetaClass.
1917 */
1918 #define OSDefineMetaClassAndFinalStructorsWithInit(className, superclassName, init) \
1919 OSDefineMetaClassWithInit(className, superclassName, init) \
1920 OSDefineFinalStructors(className, superclassName)
1921
1922
1923 /* Helpers */
1924
1925 /* Not to be included in headerdoc.
1926 *
1927 * @define OSDefineMetaClass
1928 * @hidecontents
1929 *
1930 * @abstract
1931 * Helper macro for for the standard metaclass-registration macros.
1932 * DO NOT USE.
1933 *
1934 * @param className The name of the C++ class, as a raw token,
1935 * <i>not</i> a string or macro.
1936 * @param superclassName The name of the superclass of the C++ class,
1937 * as a raw token,
1938 * <i>not</i> a string or macro.
1939 * @param init A function to call in the constructor
1940 * of the class's OSMetaClass.
1941 */
1942 #define OSDefineMetaClass(className, superclassName) \
1943 OSDefineMetaClassWithInit(className, superclassName, )
1944
1945
1946 /*!
1947 * @define OSDefineMetaClassAndStructors
1948 * @hidecontents
1949 *
1950 * @abstract
1951 * Defines an OSMetaClass and associated routines
1952 * for a concrete Libkern C++ class.
1953 *
1954 * @param className The name of the C++ class, as a raw token,
1955 * <i>not</i> a string or macro.
1956 * @param superclassName The name of the superclass of the C++ class,
1957 * as a raw token,
1958 * <i>not</i> a string or macro.
1959 *
1960 * @discussion
1961 * Concrete Libkern C++ classes should "call" this macro
1962 * at the beginning of their implementation files,
1963 * before any function implementations for the class.
1964 */
1965 #define OSDefineMetaClassAndStructors(className, superclassName) \
1966 OSDefineMetaClassAndStructorsWithInit(className, superclassName, )
1967
1968
1969 /*!
1970 * @define OSDefineMetaClassAndAbstractStructors
1971 * @hidecontents
1972 *
1973 * @abstract
1974 * Defines an OSMetaClass and associated routines
1975 * for an abstract Libkern C++ class.
1976 *
1977 * @param className The name of the C++ class, as a raw token,
1978 * <i>not</i> a string or macro.
1979 * @param superclassName The name of the superclass of the C++ class,
1980 * as a raw token,
1981 * <i>not</i> a string or macro.
1982 *
1983 * @discussion
1984 * Abstract Libkern C++ classes--those with at least one
1985 * pure virtual method--should "call" this macro
1986 * at the beginning of their implementation files,
1987 * before any function implementations for the class.
1988 */
1989 #define OSDefineMetaClassAndAbstractStructors(className, superclassName) \
1990 OSDefineMetaClassAndAbstractStructorsWithInit (className, superclassName, )
1991
1992
1993 /*!
1994 * @define OSDefineMetaClassAndFinalStructors
1995 * @hidecontents
1996 *
1997 * @abstract
1998 * Defines an OSMetaClass and associated routines
1999 * for a final (non-subclassable) Libkern C++ class.
2000 *
2001 * @param className The name of the C++ class, as a raw token,
2002 * <i>not</i> a string or macro.
2003 * @param superclassName The name of the superclass of the C++ class,
2004 * as a raw token,
2005 * <i>not</i> a string or macro.
2006 *
2007 * @discussion
2008 * Final Libkern C++ classes--those that do not allow
2009 * subclassing--should "call" this macro at the beginning
2010 * of their implementation files,
2011 * before any function implementations for the class.
2012 * (Final classes in the kernel may actually have subclasses in the kernel,
2013 * but kexts cannot define any subclasses of a final class.)
2014 *
2015 * <b>Note:</b> If the class is exported by a pseudokext (symbol set),
2016 * the final symbol generated by this macro must be exported
2017 * for the final-class attribute to be enforced.
2018 *
2019 * <b>Warning:</b> Changing a class from "Default" to "Final" will break
2020 * binary compatibility.
2021 */
2022 #define OSDefineMetaClassAndFinalStructors(className, superclassName) \
2023 OSDefineMetaClassAndFinalStructorsWithInit(className, superclassName, )
2024
2025
2026 // Dynamic vtable patchup support routines and types
2027 void reservedCalled(int ind) const;
2028
2029
2030 /*!
2031 * @define OSMetaClassDeclareReservedUnused
2032 * @hidecontents
2033 *
2034 * @abstract
2035 * Reserves vtable space for new virtual functions
2036 * in a Libkern C++ class.
2037 *
2038 * @param className The name of the C++ class, as a raw token,
2039 * <i>not</i> a string or macro.
2040 * @param index The numeric index of the vtable slot,
2041 * as a raw constant, beginning from 0.
2042 *
2043 * @discussion
2044 * Libkern C++ classes in kernel extensions that can be used as libraries
2045 * can provide for backward compatibility by declaring a number
2046 * of reserved vtable slots
2047 * that can be replaced with new functions as they are added.
2048 * Each reserved declaration must be accompanied in the implementation
2049 * by a corresponding reference to
2050 * <code>@link OSMetaClassDefineReservedUnused
2051 * OSMetaClassDefineReservedUnused@/link</code>.
2052 *
2053 * When replacing a reserved slot, change the macro from "Unused"
2054 * to "Used" to document the fact that the slot used to be reserved,
2055 * and declare the new function immediately after the "Used" macro
2056 * to preserve vtable ordering.
2057 * See
2058 * <code>@link OSMetaClassDeclareReservedUsed
2059 * OSMetaClassDeclareReservedUsed@/link</code>.
2060 */
2061 #if APPLE_KEXT_VTABLE_PADDING
2062 #define OSMetaClassDeclareReservedUnused(className, index) \
2063 private: \
2064 virtual void _RESERVED ## className ## index ()
2065 #else
2066 #define OSMetaClassDeclareReservedUnused(className, index)
2067 #endif
2068
2069
2070 /*!
2071 * @define OSMetaClassDeclareReservedUsed
2072 * @hidecontents
2073 *
2074 * @abstract
2075 * Documents use of reserved vtable space for new virtual functions
2076 * in a Libkern C++ class.
2077 *
2078 * @param className The name of the C++ class, as a raw token,
2079 * <i>not</i> a string or macro.
2080 * @param index The numeric index of the vtable slot,
2081 * as a raw constant, beginning from 0.
2082 *
2083 * @discussion
2084 * This macro evaluates to nothing, and is used to document reserved
2085 * vtable slots as they are filled.
2086 * See
2087 * <code>@link OSMetaClassDeclareReservedUnused
2088 * OSMetaClassDeclareReservedUnused@/link</code>.
2089 */
2090 #define OSMetaClassDeclareReservedUsed(className, index)
2091
2092
2093 /*!
2094 * @define OSMetaClassDefineReservedUnused
2095 * @hidecontents
2096 *
2097 * @abstract
2098 * Defines a reserved vtable slot for a Libkern C++ class.
2099 *
2100 * @param className The name of the C++ class, as a raw token,
2101 * <i>not</i> a string or macro.
2102 * @param index The numeric index of the vtable slot,
2103 * as a raw constant, beginning from 0.
2104 *
2105 * @discussion
2106 * Libkern C++ classes in kernel extensions that can be used as libraries
2107 * can provide for backward compatibility by declaring a number
2108 * of reserved vtable slots
2109 * that can be replaced with new functions as they are added.
2110 * Each reserved defintion accompanies
2111 * a corresponding declaration created with
2112 * <code>@link OSMetaClassDeclareReservedUnused
2113 * OSMetaClassDeclareReservedUnused@/link</code>.
2114 *
2115 * This macro is used in the implementation file
2116 * to provide a placeholder definition for the reserved vtable slot,
2117 * as a function that calls <code>panic</code> with an error message.
2118 *
2119 * When replacing a reserved slot, change the macro from "Unused"
2120 * to "Used" to document the fact that the slot used to be reserved,
2121 * and declare the new function immediately after the "Used" macro
2122 * to preserve vtable ordering.
2123 * See
2124 * <code>@link OSMetaClassDefineReservedUsed
2125 * OSMetaClassDefineReservedUsed@/link</code>.
2126 */
2127 #if APPLE_KEXT_VTABLE_PADDING
2128 #define OSMetaClassDefineReservedUnused(className, index) \
2129 void className ::_RESERVED ## className ## index () \
2130 { gMetaClass.reservedCalled(index); }
2131 #else
2132 #define OSMetaClassDefineReservedUnused(className, index)
2133 #endif
2134
2135
2136 /*!
2137 * @define OSMetaClassDefineReservedUsed
2138 * @hidecontents
2139 *
2140 * @abstract
2141 * Reserves vtable space for new virtual functions in a Libkern C++ class.
2142 *
2143 * @param className The name of the C++ class, as a raw token,
2144 * <i>not</i> a string or macro.
2145 * @param index The numeric index of the vtable slot,
2146 * as a raw constant, beginning from 0.
2147 *
2148 * @discussion
2149 * This macro evaluates to nothing, and is used to document reserved
2150 * vtable slots as they are filled.
2151 * See
2152 * <code>@link OSMetaClassDefineReservedUnused
2153 * OSMetaClassDefineReservedUnused@/link</code>.
2154 */
2155 #define OSMetaClassDefineReservedUsed(className, index)
2156
2157 // I/O Kit debug internal routines.
2158 static void printInstanceCounts();
2159 static void serializeClassDictionary(OSDictionary * dict);
2160 #ifdef XNU_KERNEL_PRIVATE
2161 #if IOTRACKING
2162 public:
2163 static void * trackedNew(size_t size);
2164 static void trackedDelete(void * mem, size_t size);
2165 void trackedInstance(OSObject * instance) const;
2166 void trackedFree(OSObject * instance) const;
2167 void trackedAccumSize(OSObject * instance, size_t size) const;
2168 struct IOTrackingQueue * getTracking() const;
2169 #endif /* IOTRACKING */
2170 #endif /* XNU_KERNEL_PRIVATE */
2171
2172 private:
2173 // Obsolete APIs
2174 static OSDictionary * getClassDictionary();
2175 virtual bool serialize(OSSerialize * serializer) const;
2176
2177 // Virtual Padding functions for MetaClass's
2178 OSMetaClassDeclareReservedUnused(OSMetaClass, 0);
2179 OSMetaClassDeclareReservedUnused(OSMetaClass, 1);
2180 OSMetaClassDeclareReservedUnused(OSMetaClass, 2);
2181 OSMetaClassDeclareReservedUnused(OSMetaClass, 3);
2182 OSMetaClassDeclareReservedUnused(OSMetaClass, 4);
2183 OSMetaClassDeclareReservedUnused(OSMetaClass, 5);
2184 OSMetaClassDeclareReservedUnused(OSMetaClass, 6);
2185 OSMetaClassDeclareReservedUnused(OSMetaClass, 7);
2186 };
2187
2188 #endif /* !_LIBKERN_OSMETACLASS_H */