dotgnu-pnet-commits
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[dotgnu-pnet-commits] pnet ChangeLog engine/engine.h engine/jitc.c en...


From: Klaus Treichel
Subject: [dotgnu-pnet-commits] pnet ChangeLog engine/engine.h engine/jitc.c en...
Date: Mon, 01 Jan 2007 17:09:40 +0000

CVSROOT:        /cvsroot/dotgnu-pnet
Module name:    pnet
Changes by:     Klaus Treichel <ktreichel>      07/01/01 17:09:40

Modified files:
        .              : ChangeLog 
        engine         : engine.h jitc.c jitc_alloc.c jitc_call.c 
                         jitc_delegate.c jitc_obj.c layout.c 

Log message:
        2006-01-01  Klaus Treichel  <address@hidden>
        
                * engine/engine.h: Add prototypes for the helper functions to 
create the
                type descriptors for a class.
        
                * engine/jitc.c: Add the forward declaration and libjit 
signature for the
                new function _ILJitAllocTyped.
        
                * engine/jitc_alloc.c: Add the new function _ILJitAllocTyped 
for typed
                allocation of objects and call this one in _ILJitAllocObjectGen 
if typed
                allocation is enabled.
        
                * engine/jitc_call.c: Use _ILJitAllocObjectGen instead of 
_ILJitAllocGen
                for boxing varargs.
        
                * engine/jitc_delegate.c: Use _ILJitAllocObjectGen instead of 
_ILJitAllocGen
                for boxing delegate arguments in asynchonous calls.
        
                * engine/jitc_obj.c: Use typed allocation to allocate the 
class' static
                area if typed allocation is enabled.
                Use _ILJitAllocObjectGen instead of _ILJitAllocGen to allocate 
the object
                in BoxSmaller.
                
                * engine/layout.c: Add the generation of type descriptors if 
typed
                allocation is enabled. Create the type descriptor for a class 
during layout
                if typed allocation is enabled.

CVSWeb URLs:
http://cvs.savannah.gnu.org/viewcvs/pnet/ChangeLog?cvsroot=dotgnu-pnet&r1=1.3399&r2=1.3400
http://cvs.savannah.gnu.org/viewcvs/pnet/engine/engine.h?cvsroot=dotgnu-pnet&r1=1.115&r2=1.116
http://cvs.savannah.gnu.org/viewcvs/pnet/engine/jitc.c?cvsroot=dotgnu-pnet&r1=1.62&r2=1.63
http://cvs.savannah.gnu.org/viewcvs/pnet/engine/jitc_alloc.c?cvsroot=dotgnu-pnet&r1=1.6&r2=1.7
http://cvs.savannah.gnu.org/viewcvs/pnet/engine/jitc_call.c?cvsroot=dotgnu-pnet&r1=1.32&r2=1.33
http://cvs.savannah.gnu.org/viewcvs/pnet/engine/jitc_delegate.c?cvsroot=dotgnu-pnet&r1=1.7&r2=1.8
http://cvs.savannah.gnu.org/viewcvs/pnet/engine/jitc_obj.c?cvsroot=dotgnu-pnet&r1=1.24&r2=1.25
http://cvs.savannah.gnu.org/viewcvs/pnet/engine/layout.c?cvsroot=dotgnu-pnet&r1=1.44&r2=1.45

Patches:
Index: ChangeLog
===================================================================
RCS file: /cvsroot/dotgnu-pnet/pnet/ChangeLog,v
retrieving revision 1.3399
retrieving revision 1.3400
diff -u -b -r1.3399 -r1.3400
--- ChangeLog   31 Dec 2006 19:50:41 -0000      1.3399
+++ ChangeLog   1 Jan 2007 17:09:40 -0000       1.3400
@@ -1,3 +1,30 @@
+2006-01-01  Klaus Treichel  <address@hidden>
+
+       * engine/engine.h: Add prototypes for the helper functions to create the
+       type descriptors for a class.
+
+       * engine/jitc.c: Add the forward declaration and libjit signature for 
the
+       new function _ILJitAllocTyped.
+
+       * engine/jitc_alloc.c: Add the new function _ILJitAllocTyped for typed
+       allocation of objects and call this one in _ILJitAllocObjectGen if typed
+       allocation is enabled.
+
+       * engine/jitc_call.c: Use _ILJitAllocObjectGen instead of _ILJitAllocGen
+       for boxing varargs.
+
+       * engine/jitc_delegate.c: Use _ILJitAllocObjectGen instead of 
_ILJitAllocGen
+       for boxing delegate arguments in asynchonous calls.
+
+       * engine/jitc_obj.c: Use typed allocation to allocate the class' static
+       area if typed allocation is enabled.
+       Use _ILJitAllocObjectGen instead of _ILJitAllocGen to allocate the 
object
+       in BoxSmaller.
+       
+       * engine/layout.c: Add the generation of type descriptors if typed
+       allocation is enabled. Create the type descriptor for a class during 
layout
+       if typed allocation is enabled.
+
 2006-12-31  Klaus Treichel  <address@hidden>
 
        * configure.in: Add the --enable-typedalloc option to use typed 
allocation

Index: engine/engine.h
===================================================================
RCS file: /cvsroot/dotgnu-pnet/pnet/engine/engine.h,v
retrieving revision 1.115
retrieving revision 1.116
diff -u -b -r1.115 -r1.116
--- engine/engine.h     17 Sep 2006 18:32:31 -0000      1.115
+++ engine/engine.h     1 Jan 2007 17:09:40 -0000       1.116
@@ -714,6 +714,23 @@
  */
 int _ILLayoutAlreadyDone(ILClass *info);
 
+#ifdef IL_USE_TYPED_ALLOCATION
+/*
+ * Build the type descriptor used by the garbage collector to check which words
+ * in the object have to be scanned.
+ */
+int ILGCBuildTypeDescriptor(ILClassPrivate *classPrivate,
+                                                       ILInt32 
isManagedInstance);
+
+/*
+ * Build the type descriptor used by the garbage collector to check which words
+ * in the object have to be scanned for the block holding the static fields of
+ * the class..
+ */
+ILNativeUInt ILGCBuildStaticTypeDescriptor(ILClass *classInfo,
+                                                                               
   ILInt32 isManagedStatic);
+#endif /* IL_USE_TYPED_ALLOCATION */
+
 /*
  * Verify the contents of a method.
  */

Index: engine/jitc.c
===================================================================
RCS file: /cvsroot/dotgnu-pnet/pnet/engine/jitc.c,v
retrieving revision 1.62
retrieving revision 1.63
diff -u -b -r1.62 -r1.63
--- engine/jitc.c       11 Dec 2006 20:40:11 -0000      1.62
+++ engine/jitc.c       1 Jan 2007 17:09:40 -0000       1.63
@@ -125,6 +125,13 @@
  */
 static ILObject *_ILJitAllocAtomic(ILClass *classInfo, ILUInt32 size);
 
+#ifdef IL_USE_TYPED_ALLOCATION
+/*
+ * Allocate memory for an object with a gc typedescriptor..
+ */
+static ILObject *_ILJitAllocTyped(ILClass *classInfo);
+#endif /* IL_USE_TYPED_ALLOCATION */
+
 /*
  * Definition of signatures of internal functions used by jitted code.
  * They have to be kept in sync with the corresponding engine funcions.
@@ -140,6 +147,13 @@
  */
 static ILJitType _ILJitSignature_ILJitAlloc = 0;
 
+#ifdef IL_USE_TYPED_ALLOCATION
+/*
+ * ILObject *_ILJitAllocTyped(ILClass *classInfo);
+ */
+static ILJitType _ILJitSignature_ILJitAllocTyped = 0;
+#endif /* IL_USE_TYPED_ALLOCATION */
+
 /*
  * System_Array *_ILJitSArrayAlloc(ILClass *arrayClass,
  *                                                                        
ILUInt32 numElements,
@@ -2167,6 +2181,16 @@
                return 0;
        }
 
+#ifdef IL_USE_TYPED_ALLOCATION
+       args[0] = _IL_JIT_TYPE_VPTR;
+       returnType = _IL_JIT_TYPE_VPTR;
+       if(!(_ILJitSignature_ILJitAllocTyped = 
+               jit_type_create_signature(IL_JIT_CALLCONV_CDECL, returnType, 
args, 1, 1)))
+       {
+               return 0;
+       }
+#endif /* IL_USE_TYPED_ALLOCATION */
+
        args[0] = _IL_JIT_TYPE_VPTR;
        args[1] = _IL_JIT_TYPE_UINT32;
        args[2] = _IL_JIT_TYPE_UINT32;

Index: engine/jitc_alloc.c
===================================================================
RCS file: /cvsroot/dotgnu-pnet/pnet/engine/jitc_alloc.c,v
retrieving revision 1.6
retrieving revision 1.7
diff -u -b -r1.6 -r1.7
--- engine/jitc_alloc.c 17 Oct 2006 12:24:18 -0000      1.6
+++ engine/jitc_alloc.c 1 Jan 2007 17:09:40 -0000       1.7
@@ -122,6 +122,44 @@
        return obj;
 }
 
+#ifdef IL_USE_TYPED_ALLOCATION
+/*
+ * Allocate memory for an object that contains object references.
+ */
+static ILObject *_ILJitAllocTyped(ILClass *classInfo)
+{
+       ILClassPrivate *classPrivate = (ILClassPrivate *)(classInfo->userData);
+       void *ptr;
+       ILObject *obj;
+       
+       /* Allocate memory from the heap */
+       ptr = ILGCAllocExplicitlyTyped(classPrivate->size + 
IL_OBJECT_HEADER_SIZE,
+                                                                  
classPrivate->gcTypeDescriptor);
+
+       if(!ptr)
+       {
+               /* Throw an "OutOfMemoryException" */
+               ILRuntimeExceptionThrowOutOfMemory();
+       }
+
+       obj = GetObjectFromGcBase(ptr);
+
+       /* Set the class into the block */
+       SetObjectClassPrivate(obj, classPrivate);
+
+       /* Attach a finalizer to the object if the class has
+       a non-trival finalizer method attached to it */
+       if(classPrivate->hasFinalizer)
+       {
+               ILGCRegisterFinalizer(ptr, _ILFinalizeObject,
+                                                         
classPrivate->process->finalizationContext);
+       }
+
+       /* Return a pointer to the object */
+       return obj;
+}
+#endif /* IL_USE_TYPED_ALLOCATION */
+
 /*
  * Generate the code to allocate the memory for an object with the given size.
  * Returns the ILJitValue with the pointer to the new object.
@@ -174,6 +212,10 @@
 static ILJitValue _ILJitAllocObjectGen(ILJitFunction jitFunction,
                                                                           
ILClass *classInfo)
 {
+#ifdef IL_USE_TYPED_ALLOCATION
+       ILJitValue args[1];
+#endif
+
        /* Make sure the class has been layouted. */
        if(!(classInfo->userData) || 
           (((ILClassPrivate *)(classInfo->userData))->inLayout))
@@ -183,8 +225,22 @@
                        return (ILJitValue)0;
                }
        }
+
+#ifdef IL_USE_TYPED_ALLOCATION
+       /* We call the alloc function. */
+       /* They thow an out of memory exception so we don't need to care. */
+       args[0] = jit_value_create_nint_constant(jitFunction,
+                                                                               
         _IL_JIT_TYPE_VPTR,
+                                                                               
         (jit_nint)classInfo);
+       return jit_insn_call_native(jitFunction,
+                                                               
"_ILJitAllocTyped",
+                                                               
_ILJitAllocTyped,
+                                                               
_ILJitSignature_ILJitAllocTyped,
+                                                               args, 1, 0);
+#else  /* !IL_USE_TYPED_ALLOCATION */
        return _ILJitAllocGen(jitFunction, classInfo,
                                                  ((ILClassPrivate 
*)(classInfo->userData))->size);
+#endif /* !IL_USE_TYPED_ALLOCATION */
 }
 
 #endif /* IL_JITC_FUNCTIONS */

Index: engine/jitc_call.c
===================================================================
RCS file: /cvsroot/dotgnu-pnet/pnet/engine/jitc_call.c,v
retrieving revision 1.32
retrieving revision 1.33
diff -u -b -r1.32 -r1.33
--- engine/jitc_call.c  11 Dec 2006 20:40:11 -0000      1.32
+++ engine/jitc_call.c  1 Jan 2007 17:09:40 -0000       1.33
@@ -324,11 +324,8 @@
                                                        0, paramType, 0);
                        info = ILClassResolve(info);
                        typeSize = ILSizeOfType(_thread, paramType);
-                       boxObjectSize = 
jit_value_create_nint_constant(jitCoder->jitFunction,
-                                                                               
                                   _IL_JIT_TYPE_UINT32,
-                                                                               
                                   typeSize);
 
-                       boxObject = _ILJitAllocGen(jitCoder->jitFunction, info, 
typeSize);
+                       boxObject = _ILJitAllocObjectGen(jitCoder->jitFunction, 
info);
                        if(boxValue)
                        {
                                jit_insn_store_relative(jitCoder->jitFunction,
@@ -338,6 +335,11 @@
                        }
                        else
                        {
+                               boxObjectSize =
+                                       
jit_value_create_nint_constant(jitCoder->jitFunction,
+                                                                               
                   _IL_JIT_TYPE_UINT32,
+                                                                               
                   typeSize);
+
                                jit_insn_memcpy(jitCoder->jitFunction,
                                                                boxObject,
                                                                ptr,

Index: engine/jitc_delegate.c
===================================================================
RCS file: /cvsroot/dotgnu-pnet/pnet/engine/jitc_delegate.c,v
retrieving revision 1.7
retrieving revision 1.8
diff -u -b -r1.7 -r1.8
--- engine/jitc_delegate.c      17 Oct 2006 12:24:18 -0000      1.7
+++ engine/jitc_delegate.c      1 Jan 2007 17:09:40 -0000       1.8
@@ -179,17 +179,19 @@
                                                        0, paramType, 0);
                        info = ILClassResolve(info);
                        typeSize = ILSizeOfType(_thread, paramType);
-                       boxObjectSize = 
jit_value_create_nint_constant(jitFunction,
-                                                                               
                                   _IL_JIT_TYPE_UINT32,
-                                                                               
                                   typeSize);
 
-                       boxObject = _ILJitAllocGen(jitFunction, info, typeSize);
+                       boxObject = _ILJitAllocObjectGen(jitFunction, info);
                        if(boxValue)
                        {
                                jit_insn_store_relative(jitFunction, boxObject, 
0, boxValue);
                        }
                        else
                        {
+                               boxObjectSize =
+                                       
jit_value_create_nint_constant(jitFunction,
+                                                                               
                   _IL_JIT_TYPE_UINT32,
+                                                                               
                   typeSize);
+
                                jit_insn_memcpy(jitFunction, boxObject, ptr, 
boxObjectSize);
                        }
                        jit_insn_store_relative(jitFunction,

Index: engine/jitc_obj.c
===================================================================
RCS file: /cvsroot/dotgnu-pnet/pnet/engine/jitc_obj.c,v
retrieving revision 1.24
retrieving revision 1.25
diff -u -b -r1.24 -r1.25
--- engine/jitc_obj.c   22 Oct 2006 18:01:08 -0000      1.24
+++ engine/jitc_obj.c   1 Jan 2007 17:09:40 -0000       1.25
@@ -32,19 +32,32 @@
 
        if(!classStaticData)
        {
-               ILExecThread *thread = ILExecThreadCurrent();
+               ILClassPrivate *classPrivate = (ILClassPrivate 
*)(classInfo->userData);
 
-               if(((ILClassPrivate *)(classInfo->userData))->managedStatic)
+               if(classPrivate->managedStatic)
                {
-                       classStaticData = _ILEngineAlloc(thread, 0,
-                          ((ILClassPrivate 
*)(classInfo->userData))->staticSize);
+               #ifdef  IL_USE_TYPED_ALLOCATION
+                       ILNativeInt staticTypeDescriptor =
+                               ILGCBuildStaticTypeDescriptor(classInfo, 
classPrivate->managedStatic);
+
+                       if(staticTypeDescriptor)
+                       {
+                               classStaticData = 
ILGCAllocExplicitlyTyped(classPrivate->staticSize,
+                                                                               
                                   staticTypeDescriptor);
                }
                else
                {
-                       /* There are no managed fields in the static area,
-                       so use atomic allocation */
-                       classStaticData = _ILEngineAllocAtomic(thread, 0,
-                          ((ILClassPrivate 
*)(classInfo->userData))->staticSize);
+                               classStaticData = 
ILGCAlloc(classPrivate->staticSize);
+                       }
+               #else   /* !IL_USE_TYPED_ALLOCATION */
+                       classStaticData = ILGCAlloc(classPrivate->staticSize);
+               #endif  /* !IL_USE_TYPED_ALLOCATION */
+               }
+               else
+               {
+                       /* There are no managed fields in the static area, so 
use atomic
+                          allocation */
+                       classStaticData = 
ILGCAllocAtomic(classPrivate->staticSize);
                }
                if(!classStaticData)
                {
@@ -52,7 +65,7 @@
                }
                else
                {
-                       ((ILClassPrivate *)(classInfo->userData))->staticData = 
classStaticData;
+                       classPrivate->staticData = classStaticData;
                }
        }
        return jit_value_create_nint_constant(func, _IL_JIT_TYPE_VPTR,
@@ -965,8 +978,8 @@
        jitValueType = jit_value_get_type(_ILJitStackItemValue(stackItem));
 
        /* Allocate memory */
-       newObj = _ILJitAllocGen(jitCoder->jitFunction,
-                                                       boxClass, 
jit_type_get_size(jitType));
+       newObj = _ILJitAllocObjectGen(jitCoder->jitFunction,
+                                                                 boxClass);
        
        /* If the smallerType is smaller then the initiale type then convert to 
it. */
        if(jitValueType != jitType)

Index: engine/layout.c
===================================================================
RCS file: /cvsroot/dotgnu-pnet/pnet/engine/layout.c,v
retrieving revision 1.44
retrieving revision 1.45
diff -u -b -r1.44 -r1.45
--- engine/layout.c     18 May 2006 19:34:31 -0000      1.44
+++ engine/layout.c     1 Jan 2007 17:09:40 -0000       1.45
@@ -20,6 +20,9 @@
 
 #include "engine_private.h"
 #include "il_opcodes.h"
+#ifdef IL_USE_TYPED_ALLOCATION
+#include "lib_defs.h"
+#endif /* IL_USE_TYPED_ALLOCATION */
 #if defined(HAVE_LIBFFI)
 #include "ffi.h"
 #else
@@ -56,6 +59,468 @@
  */
 static int LayoutClass(ILExecProcess *process, ILClass *info, LayoutInfo 
*layout);
 
+#ifdef IL_USE_TYPED_ALLOCATION
+/*
+ * Define offsetof macro if not present.
+ */
+#ifndef offsetof
+#define offsetof(struct_type, member) \
+          (size_t) &(((struct_type *)0)->member)
+#endif
+
+#define ILGCWordSize           (8 * sizeof(ILNativeUInt))
+#define ILGCGetBit(b, i)       (((b)[(i) / ILGCWordSize] >> ((i) % 
ILGCWordSize)) & 1)
+#define ILGCSetBit(b, i)       ((b)[(i) / ILGCWordSize] |= ((ILNativeUInt)1 << 
((i) % ILGCWordSize)))
+#define ILGCWordLen(l)         ((l) / sizeof(ILNativeUInt))
+#define ILGCWordOffset(l)      ((l) / sizeof(ILNativeUInt))
+#define ILGCBitmapSize(l)      ((ILGCWordLen(l) + ILGCWordSize - 1) / 
ILGCWordSize)
+
+#ifndef IL_CONFIG_USE_THIN_LOCKS
+/*
+ * The type desctiptor used for objects not containing any object references to
+ * be scanned by the gc.
+ */
+static ILNativeInt _ILGCObjectHeaderTypeDescriptor = 0;
+#endif /* !IL_CONFIG_USE_THIN_LOCKS */
+
+/*
+ * Inner function which does the real work.
+ */
+static int _ILGCBuildTypeDescriptor(ILClass *classInfo,
+                                                                 ILNativeUInt 
bitmap[],
+                                                                 ILNativeUInt 
checkBitmap[],
+                                                                 ILInt32 
classOffset);
+
+/*
+ * Check if the location occupied by a type not checked by the garbage 
collector
+ * is allso used by a value to be checked by the garbage collector.
+ * If there is this kind of overlapping return 0.
+ * This macro is for types with sizes <= the size of a native pointer.
+ */
+#define ILGCClearBitShort(b, cb, o, s) \
+       do { \
+               ILInt32 __startOffset = ILGCWordOffset(o); \
+               ILInt32 __endOffset = ILGCWordOffset((o) + (s) - 1); \
+               \
+               if(ILGCGetBit(cb, __startOffset)) \
+               { \
+                       if(ILGCGetBit(b, __startOffset)) \
+                       { \
+                               return 0; \
+                       } \
+               } \
+               else \
+               { \
+                       ILGCSetBit(cb, __startOffset); \
+               } \
+               if(__endOffset > __startOffset) \
+               { \
+                       if(ILGCGetBit(cb, __endOffset)) \
+                       { \
+                               if(ILGCGetBit(b, __endOffset)) \
+                               { \
+                                       return 0; \
+                               } \
+                       } \
+                       else \
+                       { \
+                               ILGCSetBit(cb, __endOffset); \
+                       } \
+               } \
+       } while(0)
+
+/*
+ * Check if the location occupied by a type not checked by the garbage 
collector
+ * is allso used by a value to be checked by the garbage collector.
+ * If there is this kind of overlapping return 0.
+ * This macro is for types with sizes > the size of a native pointer.
+ */
+#define ILGCClearBitLong(b, cb, o, s) \
+       do { \
+               ILInt32 __offset = (o); \
+               ILInt32 __gcOffset = ILGCWordOffset(o); \
+               ILInt32 __size = (s); \
+               \
+               while(__size > 0) \
+               { \
+                       if(ILGCGetBit(cb, __gcOffset)) \
+                       { \
+                               if(ILGCGetBit(b, __gcOffset)) \
+                               { \
+                                       return 0; \
+                               } \
+                       } \
+                       else \
+                       { \
+                               ILGCSetBit(cb, __gcOffset); \
+                       } \
+                       if(__size > sizeof(ILNativeUInt)) \
+                       { \
+                               __size -= sizeof(ILNativeUInt); \
+                               __offset += sizeof(ILNativeUInt); \
+                               __gcOffset++; \
+                       } \
+                       else \
+                       { \
+                               if(__gcOffset != ILGCWordOffset(__offset + 
__size - 1)) \
+                               { \
+                                       __offset += __size - 1; \
+                                       __size = 1; \
+                                       __gcOffset++; \
+                               } \
+                               else \
+                               { \
+                                       __size = 0; \
+                               } \
+                       } \
+               } \
+       } while(0)
+
+/*
+ * Set the bit for the pointer location in the bitmap and check if the same
+ * location is used by a non reference type.
+ * If there is this kind of overlapping return 0.
+ * This implemetation needs pointers at correct alligned offsets.
+ */
+#define ILGCSetBitShort(b, cb, o, s) \
+       do { \
+               ILInt32 __startOffset = ILGCWordOffset(o); \
+               \
+               if(ILGCGetBit(cb, __startOffset)) \
+               { \
+                       if(!ILGCGetBit(b, __startOffset)) \
+                       { \
+                               return 0; \
+                       } \
+               } \
+               else \
+               { \
+                       ILGCSetBit(cb, __startOffset); \
+                       ILGCSetBit(b, __startOffset); \
+               } \
+       } while(0)
+
+/*
+ * Fill the type descriptor with the type information.
+ */
+static int _ILGCBuildTypeDescriptorForType(ILType *type,
+                                                                               
 ILNativeUInt bitmap[],
+                                                                               
 ILNativeUInt checkBitmap[],
+                                                                               
 ILInt32 offset)
+{
+       type = ILTypeStripPrefixes(type);
+       if(ILType_IsPrimitive(type))
+       {
+               switch(ILType_ToElement(type))
+               {
+                       case IL_META_ELEMTYPE_BOOLEAN:
+                       case IL_META_ELEMTYPE_I1:
+                       case IL_META_ELEMTYPE_U1:
+                       {
+                               ILGCClearBitShort(bitmap, checkBitmap, offset, 
1);
+                               return 1;
+                       }
+                       break;
+
+                       case IL_META_ELEMTYPE_CHAR:
+                       case IL_META_ELEMTYPE_I2:
+                       case IL_META_ELEMTYPE_U2:
+                       {
+                               ILGCClearBitShort(bitmap, checkBitmap, offset, 
2);
+                               return 1;
+                       }
+                       break;
+
+                       case IL_META_ELEMTYPE_I4:
+                       case IL_META_ELEMTYPE_U4:
+               #ifdef IL_NATIVE_INT32
+                       case IL_META_ELEMTYPE_I:
+                       case IL_META_ELEMTYPE_U:
+               #endif  /* IL_NATIVE_INT32 */
+                       {
+                               ILGCClearBitShort(bitmap, checkBitmap, offset, 
sizeof(ILInt32));
+                               return 1;
+                       }
+                       break;
+
+                       case IL_META_ELEMTYPE_I8:
+                       case IL_META_ELEMTYPE_U8:
+               #ifdef IL_NATIVE_INT64
+                       case IL_META_ELEMTYPE_I:
+                       case IL_META_ELEMTYPE_U:
+               #endif  /* IL_NATIVE_INT64 */
+                       {
+                       #ifdef IL_NATIVE_INT32
+                               ILGCClearBitLong(bitmap, checkBitmap, offset, 
sizeof(ILInt64));
+                               return 1;
+                       #else   /* !IL_NATIVE_INT32 */
+                               ILGCClearBitShort(bitmap, checkBitmap, offset, 
sizeof(ILInt64));
+                               return 1;
+                       #endif  /* !IL_NATIVE_INT32 */
+                       }
+                       break;
+
+                       case IL_META_ELEMTYPE_R4:
+                       {
+                       #if defined(HAVE_LIBFFI)
+                               ILGCClearBitLong(bitmap, checkBitmap, offset, 
ffi_type_float.size);
+                       #else
+                               ILGCClearBitLong(bitmap, checkBitmap, offset, 
sizeof(ILFloat));
+                       #endif
+                               return 1;
+                       }
+                       break;
+
+                       case IL_META_ELEMTYPE_R8:
+                       {
+                       #if defined(HAVE_LIBFFI)
+                               ILGCClearBitLong(bitmap, checkBitmap, offset, 
ffi_type_double.size);
+                       #else
+                               ILGCClearBitLong(bitmap, checkBitmap, offset, 
sizeof(ILDouble));
+                       #endif
+                               return 1;
+                       }
+                       break;
+
+                       case IL_META_ELEMTYPE_R:
+                       {
+                       #if defined(HAVE_LIBFFI)
+                               #ifdef IL_NATIVE_FLOAT
+                                       ILGCClearBitLong(bitmap, checkBitmap, 
offset, ffi_type_longdouble.size);
+                               #else
+                                       ILGCClearBitLong(bitmap, checkBitmap, 
offset, ffi_type_double.size);
+                               #endif
+                       #else
+                               ILGCClearBitLong(bitmap, checkBitmap, offset, 
sizeof(ILNativeFloat));
+                       #endif
+                               return 1;
+                       }
+                       break;
+
+                       case IL_META_ELEMTYPE_TYPEDBYREF:
+                       {
+                               ILGCClearBitShort(bitmap, checkBitmap, offset + 
offsetof(ILTypedRef, type), sizeof(ILNativeUInt));
+                               ILGCSetBitShort(bitmap, checkBitmap, offset + 
offsetof(ILTypedRef, value), sizeof(ILNativeUInt));
+                               return 1;
+                       }
+                       break;
+
+                       default: return 0;
+               }
+       }
+       else if(ILType_IsValueType(type))
+       {
+               /* Lay out a value type by getting the full size and alignment
+                  of the class that underlies the value type */
+               ILClass *classInfo = ILClassResolve(ILType_ToValueType(type));
+               ILType *synType = ILClassGetSynType(classInfo);
+               if(synType == 0)
+               {
+                       return _ILGCBuildTypeDescriptor(classInfo,
+                                                                               
  bitmap,
+                                                                               
  checkBitmap,
+                                                                               
  offset);
+               }
+               else
+               {
+                       return 
_ILGCBuildTypeDescriptorForType(ILTypeStripPrefixes(synType),
+                                                                               
                 bitmap,
+                                                                               
                 checkBitmap,
+                                                                               
                 offset);
+               }
+       }
+       else
+       {
+               /* Everything else is laid out as a pointer */
+               if(ILTypeIsReference(ILTypeStripPrefixes(type)))
+               {
+                       ILGCSetBitShort(bitmap, checkBitmap, offset, 
sizeof(ILNativeUInt));
+               }
+               else
+               {
+                       ILGCClearBitShort(bitmap, checkBitmap, offset, 
sizeof(ILNativeUInt));
+               }
+               return 1;
+       }
+       return 0;
+}
+
+/*
+ * Inner function which does the real work.
+ */
+static int _ILGCBuildTypeDescriptor(ILClass *classInfo,
+                                                                 ILNativeUInt 
bitmap[],
+                                                                 ILNativeUInt 
checkBitmap[],
+                                                                 ILInt32 
classOffset)
+{
+       ILField *field = 0;
+
+       /* Fill the bitmap with the parent information first. */
+       if(classInfo->parent)
+       {
+               /* Use "ILClassGetParent" to resolve cross-image links */
+               ILClass *parent = ILClassGetParent(classInfo);
+
+               if(!_ILGCBuildTypeDescriptor(parent, bitmap, checkBitmap, 
classOffset))
+               {
+                       return 0;
+               }
+       }
+
+       /* Now fill the bitmaps. */
+       while((field = (ILField *)ILClassNextMemberByKind
+                       (classInfo, (ILMember *)field, 
IL_META_MEMBERKIND_FIELD)) != 0)
+       {
+               if((field->member.attributes & IL_META_FIELDDEF_STATIC) == 0)
+               {
+                       ILType *fieldType = field->member.signature;
+
+                       if(!(_ILGCBuildTypeDescriptorForType(fieldType,
+                                                                               
                 bitmap,
+                                                                               
                 checkBitmap,
+                                                                               
                 classOffset + field->offset)))
+                       {
+                               return 0;
+                       }
+               }
+       }
+       return 1;
+}
+
+/*
+ * Build the type descriptor used by the garbage collector to check which words
+ * in the object have to be scanned.
+ */
+int ILGCBuildTypeDescriptor(ILClassPrivate *classPrivate,
+                                                       ILInt32 
isManagedInstance)
+{
+       ILClass *classInfo = classPrivate->classInfo;
+       ILInt32 classSize = classPrivate->size;
+       ILInt32 bitmapSize = ILGCBitmapSize(classSize + IL_OBJECT_HEADER_SIZE);
+       ILNativeUInt bitmap[bitmapSize];
+       ILNativeUInt checkBitmap[bitmapSize];
+       ILInt32 current;
+
+       /* Clear the bitmaps first. */
+       for(current = 0; current < bitmapSize; current++)
+       {
+               bitmap[current] = 0;
+               checkBitmap[current] = 0;
+       }
+
+       if(isManagedInstance)
+       {
+       #ifndef IL_CONFIG_USE_THIN_LOCKS
+               /* Mark the location of the lock word to be traced by the gc. */
+               ILGCSetBitShort(bitmap, checkBitmap, offsetof(ILObjectHeader, 
lockWord), sizeof(ILNativeUInt));
+       #endif  /* !IL_CONFIG_USE_THIN_LOCKS */
+
+               /* Fill the bitmap with the parent information first. */
+               if(classInfo->parent)
+               {
+                       /* Use "ILClassGetParent" to resolve cross-image links 
*/
+                       ILClass *parent = ILClassGetParent(classInfo);
+
+                       if(!_ILGCBuildTypeDescriptor(parent, bitmap, 
checkBitmap, IL_OBJECT_HEADER_SIZE))
+                       {
+                               return 0;
+                       }
+               }
+
+               /* And now add the information of the current type. */
+               if(!_ILGCBuildTypeDescriptor(classInfo, bitmap, checkBitmap, 
IL_OBJECT_HEADER_SIZE))
+               {
+                       return 0;
+               }
+
+
+               /* For debugging purposes only. */
+               /*
+               for(current = 0; current < bitmapSize; current++)
+               {
+                       printf("%i; %x\n", current, bitmap[current]);
+               }
+               printf("\n");
+               */
+
+               if(!(classPrivate->gcTypeDescriptor = 
+                               ILGCCreateTypeDescriptor(bitmap, 
ILGCWordLen(classSize + IL_OBJECT_HEADER_SIZE))))
+               {
+                       return 0;
+               }
+       }
+       else
+       {
+       #ifdef IL_CONFIG_USE_THIN_LOCKS
+               classPrivate->gcTypeDescriptor = 0;
+       #else   /* !IL_CONFIG_USE_THIN_LOCKS */
+               if(_ILGCObjectHeaderTypeDescriptor == 0)
+               {
+                       /* Mark the location of the lock word to be traced by 
the gc. */
+                       ILGCSetBitShort(bitmap, checkBitmap, 
offsetof(ILObjectHeader, lockWord), sizeof(ILNativeUInt));
+
+                       if(!(_ILGCObjectHeaderTypeDescriptor = 
+                                       ILGCCreateTypeDescriptor(bitmap, 
ILGCWordLen(IL_OBJECT_HEADER_SIZE))))
+                       {
+                               return 0;
+                       }
+               }
+               classPrivate->gcTypeDescriptor = 
_ILGCObjectHeaderTypeDescriptor;
+       #endif  /* !IL_CONFIG_USE_THIN_LOCKS */
+       }
+       return 1;
+}
+
+/*
+ * Build the type descriptor used by the garbage collector to check which words
+ * in the object have to be scanned for the block holding the static fields of
+ * the class..
+ */
+ILNativeUInt ILGCBuildStaticTypeDescriptor(ILClass *classInfo,
+                                                                               
   ILInt32 isManagedStatic)
+{
+       if(isManagedStatic)
+       {
+               ILClassPrivate *classPrivate = (ILClassPrivate 
*)(classInfo->userData);
+               ILInt32 staticSize = classPrivate->staticSize;
+               ILInt32 bitmapSize = ILGCBitmapSize(staticSize);
+               ILField *field = 0;
+               ILNativeUInt bitmap[bitmapSize];
+               ILNativeUInt checkBitmap[bitmapSize];
+               ILInt32 current;
+
+               /* Clear the bitmaps first. */
+               for(current = 0; current < bitmapSize; current++)
+               {
+                       bitmap[current] = 0;
+                       checkBitmap[current] = 0;
+               }
+
+               while((field = (ILField *)ILClassNextMemberByKind
+                               (classInfo, (ILMember *)field, 
IL_META_MEMBERKIND_FIELD)) != 0)
+               {
+                       if((field->member.attributes & IL_META_FIELDDEF_STATIC) 
!= 0 &&
+                          (field->member.attributes & 
IL_META_FIELDDEF_LITERAL) == 0 &&
+                          (field->member.attributes & 
IL_META_FIELDDEF_HAS_FIELD_RVA) == 0 &&
+                          (ILFieldIsThreadStatic(field) == 0))
+                       {
+                               ILType *fieldType = field->member.signature;
+
+                               if(!(_ILGCBuildTypeDescriptorForType(fieldType,
+                                                                               
                         bitmap,
+                                                                               
                         checkBitmap,
+                                                                               
                         field->offset)))
+                               {
+                                       return 0;
+                               }
+                       }
+               }
+               return ILGCCreateTypeDescriptor(bitmap, 
ILGCWordLen(staticSize));
+       }
+       return 0;
+}
+#endif /* IL_USE_TYPED_ALLOCATION */
+
 /*
  * Get the layout information for a type.  Returns zero
  * if there is something wrong with the type.
@@ -889,6 +1354,14 @@
 #endif
        classPrivate->inLayout = 0;
 
+#ifdef IL_USE_TYPED_ALLOCATION
+       if(!ILGCBuildTypeDescriptor(classPrivate, layout->managedInstance))
+       {
+               info->userData = 0;
+               return 0;
+       }
+#endif /* IL_USE_TYPED_ALLOCATION */
+
        /* Allocate the static fields.  We must do this after the
           regular fields because some of the statics may be instances
           of the class that we are trying to lay out, especially




reply via email to

[Prev in Thread] Current Thread [Next in Thread]