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