Ignore:
Timestamp:
Jan 21, 2007, 4:58:25 PM (19 years ago)
Author:
cinc
Message:

Integration of nomUnInit() with the garbage collector using finalizers.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/nom/src/nombuildclass.c

    r199 r210  
    6767
    6868#ifdef DEBUG_NOMBUILDCLASS
    69 #define DBG_NOMBUILDCLASS(a, b, ...)   if(a) nomPrintf("%d: " b , __LINE__, __VA_ARGS__);
     69#define DBG_BUILD_LINE(a)
     70#define DBG_NOMBUILDCLASS(a, b,...)   if(a) nomPrintf("%d: " b , __LINE__,  __VA_ARGS__);
    7071#else
    71 #define DBG_NOMBUILDCLASS(a, b, ...)
     72#define DBG_NOMBUILDCLASS(a, b,...)
    7273#endif
    7374
     
    188189          //        gstr->str, sci->chrParentClassNames[a]);
    189190          if(NULL==NOMClassMgrObject)
    190             g_error("%s line %d: No overriding for base classes yet(%s)!\n",
     191            g_error("%s line %d: No overriding for base classes yet (%s)!\n",
    191192                    __FUNCTION__, __LINE__, gstr->str);
    192193          idx++; /* This is the position for the class pointer */
     
    266267    int b;
    267268
    268 #ifdef DEBUG_NOMBUILDCLASS
    269     nomPrintf(" %d: %d method(s) to override\n", __LINE__, sci->ulNumStaticOverrides);
    270 #endif
     269    DBG_NOMBUILDCLASS(TRUE, "%d method(s) to override\n", sci->ulNumStaticOverrides);
    271270
    272271    /* There're some methods to override */
     
    277276      entries=&nClass->mtab->entries[0];  /* Adress of array where we enter our resoved method */
    278277
    279 #ifdef DEBUG_NOMBUILDCLASS
    280       nomPrintf(" %d: Going to override \"%s\"\n", __LINE__, *sci->nomOverridenMethods[b].nomMethodId);
    281 #endif
     278      DBG_NOMBUILDCLASS(TRUE,"Going to override \"%s\"\n", *sci->nomOverridenMethods[b].nomMethodId);
    282279
    283280      index=priv_getIndexOfMethodInEntries(nClass, sci, *sci->nomOverridenMethods[b].nomMethodId);
     
    291288      /* Using the found index we insert our new method address into the mtab. */
    292289      entries[index]=sci->nomOverridenMethods[b].nomMethod;
     290      /* Do we just overrid nomUnInit()? Mark it because we need this info for the
     291         grabage collecting. */
     292      if(strstr(*sci->nomOverridenMethods[b].nomMethodId, ":nomUnInit"))
     293        {
     294          DBG_NOMBUILDCLASS(TRUE, "  nomUnInit() overriden.\n", "");
     295          nClass->ulClassFlags|=NOM_FLG_NOMUNINIT_OVERRIDEN; /* This flag has to be propagated down to
     296                                                                each child class. */
     297        }
    293298    } /* for(b) */ 
    294299  }/* if(sci->numStaticOverrides) */
     
    420425}
    421426
     427#if 0
     428static void priv_checkForNomUnInitOverride(  NOMClass *nomClass,  NOMClassPriv *ncpParent)
     429{
     430  /* Mark the class as using nomUnInit() if any parent did that. We just have to
     431     check the flag and the flag of the parent class. This information is important
     432     because if this method is overriden the garbage collector has to run a finalizer
     433     on the object when collecting memory so the object may do its uninit stuff. */
     434  if(nomClass && !(((NOMClassPriv*)nomClass->mtab->nomClsInfo)->ulClassFlags & NOM_FLG_NOMUNINIT_OVERRIDEN))
     435    {
     436      /* Flag not set. Try parent */
     437      if(ncpParent && ncpParent->ulClassFlags & NOM_FLG_NOMUNINIT_OVERRIDEN)
     438        ((NOMClassPriv*)nomClass->mtab->nomClsInfo)->ulClassFlags|= NOM_FLG_NOMUNINIT_OVERRIDEN;
     439    }
     440
     441  DBG_NOMBUILDCLASS(TRUE, "nomUnInit overriden in class %s: %s\n",
     442                    nomClass->mtab->nomClassName,
     443                    (((NOMClassPriv*)nomClass->mtab->nomClsInfo)->ulClassFlags & NOM_FLG_NOMUNINIT_OVERRIDEN ?
     444                     "Yes" : "No"));
     445
     446};
     447#endif
     448
     449static void priv_checkForNomUnInitOverride(  NOMClassPriv *nomClassPriv,  NOMClassPriv *ncpParent)
     450{
     451  /* Mark the class as using nomUnInit() if any parent did that. We just have to
     452     check the flag and the flag of the parent class. This information is important
     453     because if this method is overriden the garbage collector has to run a finalizer
     454     on the object when collecting memory so the object may do its uninit stuff. */
     455  DBG_NOMBUILDCLASS(TRUE, " %s (%x): %x, %s (%x): %x ", nomClassPriv->mtab->nomClassName, nomClassPriv,
     456                    nomClassPriv->ulClassFlags,
     457                    ncpParent->mtab->nomClassName, ncpParent, ncpParent->ulClassFlags);
     458  if(nomClassPriv && !(nomClassPriv->ulClassFlags & NOM_FLG_NOMUNINIT_OVERRIDEN))
     459    {
     460      /* Flag not set. Try parent */
     461      if(ncpParent && ncpParent->ulClassFlags & NOM_FLG_NOMUNINIT_OVERRIDEN)
     462        nomClassPriv->ulClassFlags|= NOM_FLG_NOMUNINIT_OVERRIDEN;
     463    }
     464
     465  DBG_NOMBUILDCLASS(TRUE, "   %x nomUnInit overriden in class %s: %s\n",
     466                    nomClassPriv->ulClassFlags, nomClassPriv->mtab->nomClassName,
     467                    (nomClassPriv->ulClassFlags & NOM_FLG_NOMUNINIT_OVERRIDEN ?
     468                     "Yes" : "No"));
     469};
     470
     471
    422472/*
    423473  This function creates a private class structure for an object from the given sci with
     
    456506    /* FIXME:       
    457507       Maybe we should panic here.  */
    458     return NULLHANDLE; /* Only SOMObject has no parent, so we have a problem here. */
     508    return NULLHANDLE; /* Only NOMObject has no parent, so we have a problem here. */
    459509  }
    460510
     
    462512  ulMemSize=sizeof(NOMClassPriv)-sizeof(nomMethodTab); /* start size class struct */
    463513
    464 #ifdef DEBUG_NOMBUILDCLASS
    465   nomPrintf("  %d: ncpParent->mtab->mtabSize: %d. Parent is: %x (priv) %s\n",
    466             __LINE__, ncpParent->mtab->mtabSize, ncpParent, ncpParent->mtab->nomClassName);
    467 #endif
     514  DBG_NOMBUILDCLASS(TRUE, "  ncpParent->mtab->mtabSize: %d. Parent is: %x (priv) %s\n",
     515                    ncpParent->mtab->mtabSize, ncpParent, ncpParent->mtab->nomClassName);
     516
    468517  mtabSize=ncpParent->mtab->mtabSize+sizeof(nomMethodProc*)*(sci->ulNumStaticMethods)+
    469518    sizeof(NOMObject*);/* numStaticMethods is correct here!
     
    474523  ulMemSize+=mtabSize; /* add place for new procs and the new class pointer */
    475524  ulParentDataSize=ncpParent->mtab->ulInstanceSize; /* Parent instance size */
    476 #ifdef DEBUG_NOMBUILDCLASS
    477   nomPrintf("  %d: %s: mtabSize will be: %d, ulParentDataSize is: %d\n", __LINE__, __FUNCTION__, mtabSize, ulParentDataSize);
    478 #endif
     525
     526  DBG_NOMBUILDCLASS(TRUE, "  %s: mtabSize will be: %d, ulParentDataSize is: %d\n"
     527                    , __FUNCTION__, mtabSize, ulParentDataSize);
     528
    479529  /* Alloc private class struct using NOMCalloc. */
    480530  if((nClass=(NOMClassPriv*)NOMCalloc(1, ulMemSize))==NULLHANDLE)
     
    496546  addMethodAndDataToThisPrivClassStruct( nClass, ncpParent, sci) ;
    497547
    498 #ifdef DEBUG_NOMBUILDCLASS
    499   nomPrintf("%d: %s:  mtab: %x\n", __LINE__, __FUNCTION__, nClass->mtab);
    500 #endif
     548  DBG_NOMBUILDCLASS(TRUE, "%s:  mtab: %x\n", __FUNCTION__, nClass->mtab);
     549
    501550  /*
    502551    Note: We don't create a class object here so the following isn't done:
     
    520569  fillCClassDataStructParentMtab(sci, nClass, nomClass);
    521570
    522 #ifdef DEBUG_NOMBUILDCLASS
    523   nomPrintf("  %d: New NOMClassPriv*: %x\n", __LINE__, nClass);
    524 #endif
     571  DBG_NOMBUILDCLASS(TRUE, "New NOMClassPriv*: %x\n", nClass);
    525572
    526573  _nomSetObjectCreateInfo(nomClass, nClass, NULLHANDLE);
    527574
     575  /* Mark the class as using nomUnInit() if any parent did that. We just have to
     576     check the flag and the flag of the parent class. This information is important
     577     because if this method is overriden the garbage collector has to run a finalizer
     578     on the object when collecting memory so the object may do its uninit stuff. */
     579  priv_checkForNomUnInitOverride( nClass,  ncpParent);
     580
    528581  DBGBUILDNOMCLASS_LEAVE
    529 
    530582  return nClass;
    531583}
     
    614666      nObject=_nomFindClassFromName(NOMClassMgrObject, sci->chrParentClassNames[a], 0, 0, NULLHANDLE);
    615667
    616       DBG_NOMBUILDCLASS( TRUE , "  %s %x %x\n" , sci->chrParentClassNames[a], nObject, NOMClassMgrObject);
    617 
     668      DBG_NOMBUILDCLASS( TRUE , "   Parent %d: %s, class object: %x\n" ,
     669                         a, sci->chrParentClassNames[a], nObject);
    618670      if(nObject){
    619         DBG_NOMBUILDCLASS( TRUE , " %s\n" , nObject->mtab->nomClassName);
     671        DBG_NOMBUILDCLASS( TRUE , "  Class object name: %s\n" , nObject->mtab->nomClassName);
    620672        if(strcmp(nObject->mtab->nomClassName, "NOMClass"))
    621           return nObject; /* Not NOMClass return */
     673          return (NOMClass*)nObject; /* Not NOMClass so return */
    622674      } /* if(nObject) */
    623675    } /* for() */
    624   return pGlobalNomEnv->defaultMetaClass;;;
     676  return pGlobalNomEnv->defaultMetaClass;
    625677}
    626678
     
    645697#ifdef DEBUG_NOMBUILDCLASS
    646698#warning !!!!! Change this when nomId is a GQuark !!!!!
    647   nomPrintf("\n\n%d: Entering %s to build %s\n", __LINE__, __FUNCTION__, *sci->nomClassId);
     699  nomPrintf("\n%d: Entering %s to build %s\n", __LINE__, __FUNCTION__, *sci->nomClassId);
    648700#endif
    649701
     
    687739
    688740#ifdef DEBUG_NOMBUILDCLASS
    689   nomPrintf("%s: New class Object (NOMClass): %x NOMClassPriv*: %x\n", __FUNCTION__, nomClass, nomClass->mtab->nomClsInfo);
    690   _dumpMtab(nomClass->mtab);
    691   _dumpObjShort(nomClass);
     741  DBG_NOMBUILDCLASS(TRUE, "%s: New class Object (NOMClass): %x NOMClassPriv*: %x ulClassFlags: %x\n",
     742                    __FUNCTION__, nomClass, nomClass->mtab->nomClsInfo,
     743                    ((NOMClassPriv*)nomClass->mtab->nomClsInfo)->ulClassFlags);
     744  //_dumpMtab(nomClass->mtab);
     745  //_dumpObjShort(nomClass);
    692746#endif
    693747
     
    773827  /* Check if already built */
    774828  if(sci->nomCds->nomClassObject) {
    775 #ifdef DEBUG_NOMBUILDCLASS
    776     nomPrintf("%d: Class %s already built. returning 0x%x\n", __LINE__, *sci->nomClassId, sci->nomCds->nomClassObject);
    777 #endif
     829    DBG_NOMBUILDCLASS(TRUE, "Class %s already built. returning 0x%x\n", *sci->nomClassId, sci->nomCds->nomClassObject);
    778830    return (sci->nomCds)->nomClassObject; /* Yes,return the object */
    779831  }
     
    788840  if(!strcmp(*sci->nomClassId, "NOMObject")){
    789841    if(pGlobalNomEnv->ncpNOMObject!=NULLHANDLE){
    790 #ifdef DEBUG_NOMBUILDCLASS
    791       nomPrintf("%d: Class %s already built. returning 0x%x\n", __LINE__, *sci->nomClassId, sci->nomCds->nomClassObject);
    792 #endif
     842      DBG_NOMBUILDCLASS(TRUE, "Class %s already built. returning 0x%x\n",
     843                        *sci->nomClassId, sci->nomCds->nomClassObject);
    793844      /* FIXME: this seems to be broken!! */
    794       return NULLHANDLE; /* SOMObject already built */
     845      return NULLHANDLE; /* NOMObject already built */
    795846    }
    796847  }
    797848
    798849#ifdef _DEBUG_NOMBUILDCLASS
    799   nomPrintf("%d: Dumping sci:\n", __LINE__);
     850  DBG_NOMBUILDCLASS(TRUE, "Dumping sci:\n");
    800851  _dumpSci(sci);
    801852#endif
     
    830881  /* Do we want to build NOMObject the mother of all classes? */
    831882  if(!strcmp(*sci->nomClassId, "NOMObject")){
    832 #ifdef DEBUG_NOMBUILDCLASS
    833     nomPrintf("%d: Trying to build  %s\n", __LINE__, *sci->nomClassId);
    834 #endif
     883
     884    DBG_NOMBUILDCLASS(TRUE, "Trying to build  %s\n", *sci->nomClassId);
     885
    835886    priv_buildNOMObjectClassInfo(ulReserved, sci, /* yes */
    836887                                 ulMajorVersion, ulMinorVersion);
     
    869920#ifdef DEBUG_NOMBUILDCLASS
    870921  /* Do some debugging here... */
    871   nomPrintf("%d: Found parent private class info struct. Dumping parentMTabStruct...\n", __LINE__);
     922  DBG_NOMBUILDCLASS(TRUE, "Found parent private class info struct. Dumping parentMTabStruct...\n", NULL);
    872923  pParentMtab=&ncpParent->parentMtabStruct;
    873   nomPrintf("     parent class: %s (priv %x), pParentMtab: %x, pParentMtab->mtab %x, next: %x\n", ncpParent->mtab->nomClassName,
     924  nomPrintf("     parent class: %s (priv %x), pParentMtab: %x, pParentMtab->mtab %x, next: %x\n",
     925            ncpParent->mtab->nomClassName,
    874926            ncpParent, pParentMtab, pParentMtab->mtab, pParentMtab->next);
    875927  /* climb parent list */
     
    886938    /* No, parent of class to build is normal object so we have to use either an explicit meta class if given or
    887939       another NOMClass derived class for the class object. */
    888 #ifdef DEBUG_NOMBUILDCLASS
    889     nomPrintf("%d: Class %x (ncpParent->mtab->nomClassName: %s) is not a NOMClass\n",
    890               __LINE__, ncpParent, ncpParent->mtab->nomClassName);
    891 #endif
     940
     941    DBG_NOMBUILDCLASS(TRUE, "Class %x (ncpParent->mtab->nomClassName: %s) is not a NOMClass\n",
     942                      ncpParent, ncpParent->mtab->nomClassName);
    892943
    893944    if(sci->nomExplicitMetaId)
     
    896947           with the info how to create objects. */
    897948
    898 #ifdef DEBUG_NOMBUILDCLASS
    899         nomPrintf("%d: sci->nomExplicitMetaId is set. Calling priv_buildWithExplicitMetaClass().\n", __LINE__);
    900 #endif
     949        DBG_NOMBUILDCLASS(TRUE, "sci->nomExplicitMetaId is set. Calling priv_buildWithExplicitMetaClass().\n", "");
    901950   
    902951        nomClass= priv_buildWithExplicitMetaClass(ulReserved, sci,
    903952                                                  ulMajorVersion, ulMinorVersion);
    904953        if(nomClass){
    905 #ifdef DEBUG_NOMBUILDCLASS
    906           nomPrintf("%d: %s: class is 0x%x\n", __LINE__, nomClass->mtab->nomClassName, nomClass);
    907 #endif   
    908           _nomInit(nomClass, NULLHANDLE);
     954          DBG_NOMBUILDCLASS(TRUE, "%s: class is 0x%x\n", nomClass->mtab->nomClassName, nomClass);
     955#if 0
     956          /* Mark the class as using nomUnInit() if any parent did that. We just have to
     957             check the flag and the flag of the parent class. This information is important
     958             because if this method is overriden the garbage collector has to run a finalizer
     959             on the object when collecting memory so the object may do its uninit stuff. */
     960          priv_checkForNomUnInitOverride( (NOMClassPriv*)nomClass->mtab->nomClsInfo,  ncpParent);
     961#endif     
     962          _nomInit((NOMObject*)nomClass, NULLHANDLE);
    909963          _nomClassReady(nomClass, NULLHANDLE);
    910964        }
     
    915969      /* Use NOMClass derived class as meta class. We have to climb the parent list of this object class
    916970         to check if one parent introduced an explicit metaclass. If yes, we have to use that one as
    917          the metaclass. IF no parent did that we just use NOMClass.
     971         the metaclass. If no parent did that we just use NOMClass.
    918972         The following call will create the class object and will also fill in the necessary object info for
    919973         creating instances. */
     
    922976
    923977      if(nomClass){
    924         //#warning !!!!! No call of  _nomClassReady() here !!!!!
    925         //#if 0
    926         _nomInit(nomClass, NULLHANDLE);
    927         _nomClassReady(nomClass, NULLHANDLE);   
    928         //#endif
     978        _nomInit((NOMObject*)nomClass, NULLHANDLE);
     979        _nomClassReady(nomClass, NULLHANDLE);
    929980      }
    930981      return nomClass;
     
    938989
    939990  /* Calculate size of new class object */
    940 #ifdef DEBUG_NOMBUILDCLASS
    941   nomPrintf("%d: Parent class 0x%x (ncpParent->mtab->nomClassName: %s) is a NOMClass (or derived)\n",
    942             __LINE__, ncpParent, ncpParent->mtab->nomClassName);
    943   nomPrintf("      ncParent->mtab->mtabSize: %d\n", ncpParent->mtab->mtabSize);
    944 #endif
     991  DBG_NOMBUILDCLASS(TRUE, "Parent class 0x%x (ncpParent->mtab->nomClassName: %s) is a NOMClass (or derived)\n",
     992                    ncpParent, ncpParent->mtab->nomClassName);
     993  DBG_NOMBUILDCLASS(TRUE, "      ncParent->mtab->mtabSize: %d\n", ncpParent->mtab->mtabSize);
     994
    945995  mtabSize=ncpParent->mtab->mtabSize+sizeof(nomMethodProc*)*(sci->ulNumStaticMethods)+sizeof(NOMClass*);/* ulNumStaticMethods is correct here!
    946996                                                                                                        NOT numStaticMethods-1!
     
    9511001  ulParentDataSize=ncpParent->mtab->ulInstanceSize; /* Parent instance size */
    9521002 
    953 #ifdef DEBUG_NOMBUILDCLASS
    954   nomPrintf("%d: %s mtabSize is: %d, ulParentDataSize is: %d\n", __LINE__, *sci->nomClassId, mtabSize, ulParentDataSize);
    955 #endif
    956 
     1003  DBG_NOMBUILDCLASS(TRUE, "%s mtabSize is: %d, ulParentDataSize is: %d\n",
     1004                    *sci->nomClassId, mtabSize, ulParentDataSize);
    9571005
    9581006  /* Alloc class struct using NOMCalloc. */
     
    9861034
    9871035  nomClass->mtab=nClass->mtab; 
    988 #ifdef DEBUG_NOMBUILDCLASS
    989   nomPrintf("%d: mtab: %x, nClass: 0x%x, nomClass: 0x%x\n", __LINE__, nClass->mtab, nClass, nomClass);
    990 #endif
     1036
     1037  DBG_NOMBUILDCLASS(TRUE,"mtab: %x, nClass: 0x%x, nomClass: 0x%x\n", nClass->mtab, nClass, nomClass);
     1038
    9911039  sci->nomCds->nomClassObject=nomClass; /* Put class pointer in static struct */
    9921040
     
    10111059  // _nomSetInstanceSize(nomClass, sci->ulInstanceDataSize+ulParentDataSize);
    10121060
    1013 #ifdef DEBUG_NOMBUILDCLASS
    1014   nomPrintf("%d: New class ptr (class object): %x (NOMClassPriv: %x) for %s\n", __LINE__, nomClass, nClass, *sci->nomClassId);
    1015 #endif
    1016 
    1017   //priv_addPrivClassToGlobalClassList(pGlobalNomEnv, nClass);
    1018   _nomInit(nomClass, NULLHANDLE);
    1019   _nomClassReady(nomClass, NULLHANDLE);
     1061  DBG_NOMBUILDCLASS(TRUE, "New class ptr (class object): %x (NOMClassPriv: %x) for %s\n"
     1062                    , nomClass, nClass, *sci->nomClassId);
     1063
     1064  if(nomClass){
     1065    /* Mark the class as using nomUnInit() if any parent did that. We just have to
     1066       check the flag and the flag of the parent class. This information is important
     1067       because if this method is overriden the garbage collector has to run a finalizer
     1068       on the object when collecting memory so the object may do its uninit stuff. */
     1069    priv_checkForNomUnInitOverride( (NOMClassPriv*)nomClass->mtab->nomClsInfo,  ncpParent);
     1070   
     1071    _nomInit(nomClass, NULLHANDLE);
     1072    _nomClassReady(nomClass, NULLHANDLE);
     1073  }
    10201074  return nomClass;
    10211075};
     1076
     1077
     1078
     1079
    10221080
    10231081
     
    10251083/*     Unused stuff */
    10261084/*********************************************************************************************************************/
    1027 
    1028 
    1029 
    10301085#if 0
    10311086#include <cwsomcls.h>
Note: See TracChangeset for help on using the changeset viewer.