objc-class.h

Go to the documentation of this file.
00001 /*
00002  * Copyright (c) 1999 Apple Computer, Inc. All rights reserved.
00003  *
00004  * @APPLE_LICENSE_HEADER_START@
00005  * 
00006  * Portions Copyright (c) 1999 Apple Computer, Inc.  All Rights
00007  * Reserved.  This file contains Original Code and/or Modifications of
00008  * Original Code as defined in and that are subject to the Apple Public
00009  * Source License Version 1.1 (the "License").  You may not use this file
00010  * except in compliance with the License.  Please obtain a copy of the
00011  * License at http://www.apple.com/publicsource and read it before using
00012  * this file.
00013  * 
00014  * The Original Code and all software distributed under the License are
00015  * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
00016  * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
00017  * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
00018  * FITNESS FOR A PARTICULAR PURPOSE OR NON- INFRINGEMENT.  Please see the
00019  * License for the specific language governing rights and limitations
00020  * under the License.
00021  * 
00022  * @APPLE_LICENSE_HEADER_END@
00023  */
00024 /*
00025  *  objc-class.h
00026  *  Copyright 1988-1996, NeXT Software, Inc.
00027  */
00028 
00029 #ifndef _OBJC_CLASS_H_
00030 #define _OBJC_CLASS_H_
00031 
00032 #include "objc/objc.h"
00033 /* 
00034  *  Class Template
00035  */
00036 struct objc_class {         
00037     struct objc_class *isa; 
00038     struct objc_class *super_class; 
00039     const char *name;       
00040     long version;
00041     long info;
00042     long instance_size;
00043     struct objc_ivar_list *ivars;
00044 
00045     struct objc_method_list **methodLists;
00046 
00047     struct objc_cache *cache;
00048     struct objc_protocol_list *protocols;
00049 };
00050 #define CLS_GETINFO(cls,infomask)   ((cls)->info & (infomask))
00051 #define CLS_SETINFO(cls,infomask)   ((cls)->info |= (infomask))
00052 
00053 #define CLS_CLASS       0x1L
00054 #define CLS_META        0x2L
00055 #define CLS_INITIALIZED     0x4L
00056 #define CLS_POSING      0x8L
00057 #define CLS_MAPPED      0x10L
00058 #define CLS_FLUSH_CACHE     0x20L
00059 #define CLS_GROW_CACHE      0x40L
00060 #define CLS_NEED_BIND       0x80L
00061 #define CLS_METHOD_ARRAY        0x100L
00062 // the JavaBridge constructs classes with these markers
00063 #define CLS_JAVA_HYBRID     0x200L
00064 #define CLS_JAVA_CLASS      0x400L
00065 // thread-safe +initialize
00066 #define CLS_INITIALIZING    0x800
00067 
00068 /*
00069  * (true as of 2001-9-24)
00070  * Thread-safety note: changes to these flags are not atomic, so 
00071  * the only thing preventing lost updates is the timing of the changes.
00072  *
00073  * As long as the following are isolated from each other for any one class, 
00074  * nearly all flag updates will be safe:
00075  * - compile-time
00076  * - loading in one thread (not including +load) without messaging
00077  * - initializing in one thread with messaging from that thread only
00078  * - multi-threaded messaging with method caching
00079  *
00080  * The current code doesn't protect loading yet.
00081  *
00082  * Times when the flags may change:
00083  * CLS_CLASS: compile-time, hand-built classes
00084  * CLS_META: compile time, hand-built classes
00085  * CLS_INITIALIZED: initialize
00086  * CLS_POSING: unsafe, but posing has other thread-safety problems
00087  * CLS_MAPPED: compile-time
00088  * CLS_FLUSH_CACHE: messaging
00089  * CLS_GROW_CACHE: messaging
00090  *   FLUSH_CACHE and GROW_CACHE are protected from each other by the 
00091  *   cacheUpdateLock.
00092  * CLS_NEED_BIND: load, initialize
00093  * CLS_METHOD_ARRAY: load
00094  * CLS_JAVA_HYBRID: hand-built classes
00095  * CLS_JAVA_CLASS: hand-built classes, initialize
00096  * CLS_INITIALIZING: initialize
00097  *
00098  * The only unsafe updates are:
00099  * - posing (unsafe anyway)
00100  * - hand-built classes (including JavaBridge classes)
00101  *   There is a short time between objc_addClass inserts the new class 
00102  *   into the class_hash and the builder setting the right flags. 
00103  *   A thread looking at the class_hash could send a message to the class 
00104  *   and trigger initialization, and the changes to the initialization 
00105  *   flags and the hand-adjusted flags could collide. 
00106  *   Solution: don't do that. 
00107  */
00108 
00109 
00110 /* 
00111  *  Category Template
00112  */
00113 typedef struct objc_category *Category;
00114 
00115 struct objc_category {
00116     char *category_name;
00117     char *class_name;
00118     struct objc_method_list *instance_methods;
00119     struct objc_method_list *class_methods;
00120     struct objc_protocol_list *protocols;
00121 };
00122 
00123 /* 
00124  *  Instance Variable Template
00125  */
00126 typedef struct objc_ivar *Ivar;
00127 
00128 struct objc_ivar {
00129     char *ivar_name;
00130     char *ivar_type;
00131     int ivar_offset;
00132 #ifdef __alpha__
00133     int space;
00134 #endif
00135 };
00136 
00137 struct objc_ivar_list {
00138     int ivar_count;
00139 #ifdef __alpha__
00140     int space;
00141 #endif
00142     struct objc_ivar ivar_list[1];      /* variable length structure */
00143 };
00144 
00145 OBJC_EXPORT Ivar object_setInstanceVariable(id, const char *name, void *);
00146 OBJC_EXPORT Ivar object_getInstanceVariable(id, const char *name, void **);
00147 
00148 /* 
00149  *  Method Template
00150  */
00151 typedef struct objc_method *Method;
00152 
00153 struct objc_method {
00154     SEL method_name;
00155     char *method_types;
00156     IMP method_imp;
00157 };
00158 
00159 struct objc_method_list {
00160     struct objc_method_list *obsolete;
00161 
00162     int method_count;
00163 #ifdef __alpha__
00164     int space;
00165 #endif
00166     struct objc_method method_list[1];  /* variable length structure */
00167 };
00168 
00169 /* Protocol support */
00170 
00171 //@class Protocol;
00172 struct Protocol;
00173 
00174 struct objc_protocol_list {
00175     struct objc_protocol_list *next;
00176     int count;
00177     Protocol *list[1];
00178 };
00179 
00180 /* Definitions of filer types */
00181 
00182 #define _C_ID       '@'
00183 #define _C_CLASS    '#'
00184 #define _C_SEL      ':'
00185 #define _C_CHR      'c'
00186 #define _C_UCHR     'C'
00187 #define _C_SHT      's'
00188 #define _C_USHT     'S'
00189 #define _C_INT      'i'
00190 #define _C_UINT     'I'
00191 #define _C_LNG      'l'
00192 #define _C_ULNG     'L'
00193 #define _C_FLT      'f'
00194 #define _C_DBL      'd'
00195 #define _C_BFLD     'b'
00196 #define _C_VOID     'v'
00197 #define _C_UNDEF    '?'
00198 #define _C_PTR      '^'
00199 #define _C_CHARPTR  '*'
00200 #define _C_ARY_B    '['
00201 #define _C_ARY_E    ']'
00202 #define _C_UNION_B  '('
00203 #define _C_UNION_E  ')'
00204 #define _C_STRUCT_B '{'
00205 #define _C_STRUCT_E '}'
00206 
00207 /* Structure for method cache - allocated/sized at runtime */
00208 
00209 typedef struct objc_cache * Cache;
00210 
00211 #define CACHE_BUCKET_NAME(B)  ((B)->method_name)
00212 #define CACHE_BUCKET_IMP(B)   ((B)->method_imp)
00213 #define CACHE_BUCKET_VALID(B) (B)
00214 #define CACHE_HASH(sel, mask) (((uarith_t)(sel)>>2) & (mask))
00215 struct objc_cache {
00216     unsigned int mask;            /* total = mask + 1 */
00217     unsigned int occupied;        
00218     Method buckets[1];
00219 };
00220 
00221 /* operations */
00222 OBJC_EXPORT id class_createInstance(Class, unsigned idxIvars);
00223 OBJC_EXPORT id class_createInstanceFromZone(Class, unsigned idxIvars, void *z);
00224 
00225 OBJC_EXPORT void class_setVersion(Class, int);
00226 OBJC_EXPORT int class_getVersion(Class);
00227 
00228 OBJC_EXPORT Ivar class_getInstanceVariable(Class, const char *);
00229 OBJC_EXPORT Method class_getInstanceMethod(Class, SEL);
00230 OBJC_EXPORT Method class_getClassMethod(Class, SEL);
00231 
00232 OBJC_EXPORT void class_addMethods(Class, struct objc_method_list *);
00233 OBJC_EXPORT void class_removeMethods(Class, struct objc_method_list *);
00234 
00235 OBJC_EXPORT Class class_poseAs(Class imposter, Class original);
00236 
00237 OBJC_EXPORT unsigned method_getNumberOfArguments(Method);
00238 OBJC_EXPORT unsigned method_getSizeOfArguments(Method);
00239 OBJC_EXPORT unsigned method_getArgumentInfo(Method m, int arg, const char **type, int *offset);
00240 
00241 // usage for nextMethodList
00242 //
00243 // void *iterator = 0;
00244 // struct objc_method_list *mlist;
00245 // while ( mlist = class_nextMethodList( cls, &iterator ) )
00246 //    ;
00247 #define OBJC_NEXT_METHOD_LIST 1
00248 OBJC_EXPORT struct objc_method_list *class_nextMethodList(Class, void **);
00249 
00250 typedef void *marg_list;
00251 
00252 #if defined(__ppc__) || defined(ppc)
00253 #define marg_prearg_size    128
00254 #else
00255 #define marg_prearg_size    0
00256 #endif
00257 
00258 #define marg_malloc(margs, method) \
00259     do { \
00260         margs = (marg_list *)malloc (marg_prearg_size + ((7 + method_getSizeOfArguments(method)) & ~7)); \
00261     } while (0)
00262 
00263 
00264 #define marg_free(margs) \
00265     do { \
00266         free(margs); \
00267     } while (0)
00268     
00269 #define marg_adjustedOffset(method, offset) \
00270     (marg_prearg_size + offset)
00271 
00272 
00273 
00274 
00275 #define marg_getRef(margs, offset, type) \
00276     ( (type *)((char *)margs + marg_adjustedOffset(method,offset) ) )
00277 
00278 #define marg_getValue(margs, offset, type) \
00279     ( *marg_getRef(margs, offset, type) )
00280 
00281 #define marg_setValue(margs, offset, type, value) \
00282     ( marg_getValue(margs, offset, type) = (value) )
00283 
00284 /* Load categories and non-referenced classes from libraries. */
00285 
00286 #endif /* _OBJC_CLASS_H_ */

Generated on Tue Sep 19 21:18:25 2006 for Boomerang by  doxygen 1.4.6