00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00014 
00015 
00016 
00017 
00018 
00019 
00020 
00021 
00022 
00023 
00024 
00025 
00026 
00027 
00028 
00029 
00030 
00031 
00032 
00033 
00034 
00035 
00036 
00037 
00038 
00039 
00040 
00041 
00042 
00043 
00044 
00045 
00046 
00047 
00048 
00049 
00050 
00051 
00052 
00053 
00054 
00055 
00056 
00057 
00058 
00059 
00060 
00061 
00062 
00063 
00064 
00065 
00066 
00067 
00068 
00069 
00070 
00071 
00072 
00073 
00074 
00075 
00076 
00077 
00078 
00079 
00080 
00081 
00082 
00083 
00084 
00085 
00086 
00087 
00088 
00089 
00090 
00091 
00092 
00093 
00094 
00095 
00096 
00097 
00098 
00099 
00100 
00101 
00102 #include <stdlib.h>
00103 #include <string.h>
00104 
00105 #ifdef _DEBUG
00106 #include <stdio.h>
00107 #endif
00108 
00109 #include "errcodes.h"
00110 #include "memory.h"
00111 #include "myalloc.h"
00112 
00113 
00114 
00115 
00116 
00117 
00118 
00119 
00120 
00121 
00122 int memory_InitStructure(pMemoryObject pMo
00123   ){
00124 
00125 
00126 
00127 
00128 
00129 
00130 
00131 
00132 
00133   memset(pMo->SizeOfType,0,sizeof(long)*MAX_NUMBER_OF_FIX_TYPES);
00134   memset(pMo->MemoryObjectsFreeList,0,sizeof(void *)*MAX_NUMBER_OF_FIX_TYPES);
00135   pMo->iNumberOfFixTypes = MAX_FIX_TYPE; 
00136 
00137   pMo->pMemorySegment = alloc_InitSegment(pMo->memory_allocating_function,pMo->memory_releasing_function);
00138   if( pMo->pMemorySegment == NULL )return MEM_ERROR_MEMORY_LOW;
00139   return MEM_ERROR_SUCCESS;
00140   }
00141 
00142 
00143 
00144 
00145 
00146 
00147 
00148 
00149 int memory_RegisterType(pMemoryObject pMo,
00150                         unsigned long SizeOfThisType
00151   ){
00152 
00153 
00154 
00155 
00156 
00157 
00158   if( pMo->iNumberOfFixTypes >= MAX_NUMBER_OF_FIX_TYPES )return -1;
00159   pMo->SizeOfType[pMo->iNumberOfFixTypes++] = SizeOfThisType;
00160   return pMo->iNumberOfFixTypes-1;
00161   }
00162 
00163 
00164 
00165 
00166 
00167 
00168 
00169 
00170 
00171 
00172 void memory_RegisterTypes(pMemoryObject pMo
00173   ){
00174 
00175 
00176 
00177 
00178 
00179 
00180 
00181 
00182 
00183 
00184 
00185 
00186 
00187 
00188   pMo->FirstStringIndex = memory_RegisterType(pMo,32);
00189                           memory_RegisterType(pMo,64);
00190                           memory_RegisterType(pMo,128);
00191                           memory_RegisterType(pMo,256);
00192                           memory_RegisterType(pMo,512);
00193   pMo->LastStringIndex = memory_RegisterType(pMo,1024);
00194   }
00195 
00196 #ifdef _DEBUG
00197 
00198 
00199 
00200 
00201 
00202 
00203 
00204 void memory_DebugDump(pMemoryObject pMo
00205   ){
00206 
00207 
00208   pFixSizeMemoryObject p;
00209   int i;
00210   unsigned long count;
00211 
00212   for( i = pMo->FirstStringIndex ; i <= pMo->LastStringIndex ; i++ ){
00213     p = pMo->MemoryObjectsFreeList[i];
00214     count = 0;
00215     while( p ){
00216       p = p->next;
00217       count++;
00218       }
00219     printf("list %d. length=%d\n",i,count);
00220     }
00221 
00222   }
00223 #endif
00224 
00225 
00226 
00227 
00228 
00229 
00230 
00231 
00232 
00233 
00234 
00235 pFixSizeMemoryObject memory_NewVariable(pMemoryObject pMo,
00236                                         int type,
00237                                         unsigned long LargeBlockSize
00238   ){
00239 
00240 
00241 
00242 
00243 
00244 
00245 
00246 
00247 
00248 
00249 
00250   pFixSizeMemoryObject p;
00251   int atype; 
00252 
00253   if( type == LARGE_BLOCK_TYPE ){
00254     p = alloc_Alloc(sizeof(FixSizeMemoryObject),pMo->pMemorySegment);
00255     if( p == NULL )return NULL;
00256     p->sType = type;
00257     p->State = STATE_UNKNOWN;
00258     p->next = NULL;
00259     p->link.prev = NULL;
00260     p->ArrayHighLimit = 0;
00261     p->ArrayLowLimit  = 1;
00262     p->Size = LargeBlockSize;
00263     p->Value.pValue = alloc_Alloc(LargeBlockSize,pMo->pMemorySegment);
00264     if( p->Value.pValue == NULL ){
00265       alloc_Free(p,pMo->pMemorySegment);
00266       return NULL;
00267       }
00268     return p;
00269     }
00270 
00271   if( type >= MAX_NUMBER_OF_FIX_TYPES )return NULL;
00272 
00273   
00274 
00275 
00276   if( type < MAX_FIX_TYPE )
00277     atype = FIX_TYPE_ALLOC;
00278   else
00279     atype = type;
00280 
00281   
00282   if( pMo->MemoryObjectsFreeList[atype] == NULL ){
00283     p = alloc_Alloc(sizeof(FixSizeMemoryObject),pMo->pMemorySegment);
00284     if( p == NULL )return NULL;
00285     p->sType = type;
00286     p->State = STATE_UNKNOWN;
00287     p->next = NULL;
00288     p->link.prev = NULL;
00289     
00290     if( pMo->SizeOfType[type] != 0 ){
00291       p->Value.pValue = alloc_Alloc(pMo->SizeOfType[type],pMo->pMemorySegment);
00292       if( p->Value.pValue == NULL ){
00293         alloc_Free(p,pMo->pMemorySegment);
00294         return NULL;
00295         }
00296       }else{
00297       p->Value.pValue = NULL;
00298       }
00299     return p;
00300     }
00301 
00302   p = pMo->MemoryObjectsFreeList[atype];
00303   pMo->MemoryObjectsFreeList[atype] = pMo->MemoryObjectsFreeList[atype]->next;
00304   if( pMo->MemoryObjectsFreeList[atype] )
00305     pMo->MemoryObjectsFreeList[atype]->link.prev = NULL;
00306 
00307   p->sType = type;
00308   p->next = NULL;
00309   p->link.prev = NULL;
00310   p->ArrayHighLimit = 0;
00311   p->ArrayLowLimit  = 1;
00312   p->State = STATE_UNKNOWN;
00313   return p;
00314   }
00315 
00316 
00317 
00318 
00319 
00320 
00321 
00322 int memory_ReleaseVariable(pMemoryObject pMo,
00323                            pFixSizeMemoryObject p
00324   ){
00325 
00326 
00327   long i;
00328   int atype; 
00329   pFixSizeMemoryObject *pRefHead,*pRef,pSwap;
00330 #ifdef _DEBUG
00331 pFixSizeMemoryObject q;
00332 static int dbgc=0;
00333 #endif
00334   
00335   if( p == NULL )return 0;
00336 
00337 #ifdef _DEBUG
00338   if( p->sType != LARGE_BLOCK_TYPE ){
00339     q = pMo->MemoryObjectsFreeList[p->sType];
00340     while( q ){
00341       if( q == p ){
00342         printf("A released memory location is rereleased.\n");
00343         exit(666);
00344         }
00345       q = q->next;
00346       }
00347    }
00348 #endif
00349 
00350   
00351 
00352   if( p->State == STATE_IMMORTAL && p->link.rprev && p->vType != VTYPE_REF){
00353     
00354 
00355 
00356     pRefHead = p->link.rprev;
00357     
00358     pRef = (*pRefHead)->link.rprev;
00359     
00360     pSwap = p;
00361     p = *pRefHead;
00362     *pRefHead = pSwap;
00363     
00364 
00365 
00366 
00367     (*pRefHead)->link.rprev = pRef;
00368     
00369     (*pRefHead)->next = NULL;
00370     if( pRef )(*pRef)->next = *pRefHead;
00371     
00372     while( pRef ){
00373       (*pRef)->Value.aValue = pRefHead;
00374       pRef = (*pRef)->link.rprev;
00375       }
00376     }else{
00377 
00378 
00379 
00380 
00381     if( p->State == STATE_IMMORTAL && p->vType == VTYPE_REF ){
00382       if( p->next )
00383         p->next->link.rprev = p->link.rprev;
00384       if( p->link.rprev )
00385         (*(p->link.rprev))->next = p->next;
00386       p->link.rprev = NULL;
00387       p->next = NULL;
00388       }
00389     }
00390   
00391   if( p->vType == VTYPE_ARRAY ){
00392     for( i = p->ArrayLowLimit ; i<= p->ArrayHighLimit ; i++ )
00393       if( p->Value.aValue[i - p->ArrayLowLimit] )
00394         memory_ReleaseVariable(pMo,p->Value.aValue[i - p->ArrayLowLimit]);
00395     }
00396 
00397   
00398   if( p->sType == LARGE_BLOCK_TYPE ){
00399     if( p->Value.pValue )
00400       alloc_Free(p->Value.pValue,pMo->pMemorySegment);
00401     alloc_Free(p,pMo->pMemorySegment);
00402     return 0;
00403     }
00404 
00405   
00406 
00407 
00408   if( p->sType < MAX_FIX_TYPE )
00409     atype = FIX_TYPE_ALLOC;
00410   else
00411     atype = p->sType;
00412 
00413   
00414   p->next = pMo->MemoryObjectsFreeList[atype];
00415   p->link.prev = NULL;
00416   if( p->next )
00417     p->next->link.prev = p;
00418   p->State = STATE_FREE;
00419   pMo->MemoryObjectsFreeList[atype] = p;
00420   return 0;
00421   }
00422 
00423 
00424 
00425 
00426 
00427 
00428 pFixSizeMemoryObject memory_NewString(pMemoryObject pMo,
00429                                       unsigned long StringSize
00430   ){
00431 
00432 
00433 
00434 
00435 
00436 
00437 
00438 
00439   BYTE i;
00440   pFixSizeMemoryObject p;
00441 
00442   for( i=pMo->FirstStringIndex ; i<= pMo->LastStringIndex ; i++ ){
00443     if( StringSize <= pMo->SizeOfType[i] ){
00444       p = memory_NewVariable(pMo,i,0);
00445       if( p == NULL )return NULL;
00446       p->vType = VTYPE_STRING;
00447       p->Size = StringSize;
00448       return p;
00449       }
00450     }
00451   p = memory_NewVariable(pMo,(int)LARGE_BLOCK_TYPE,StringSize);
00452   if( p == NULL )return NULL;
00453   p->vType = VTYPE_STRING;
00454   return p;
00455   }
00456 
00457 
00458 
00459 
00460 
00461 
00462 pFixSizeMemoryObject memory_NewCString(pMemoryObject pMo,
00463                                        unsigned long StringSize
00464   ){
00465 
00466 
00467 
00468 
00469   pFixSizeMemoryObject p;
00470 
00471   p = memory_NewVariable(pMo,FIX_TYPE_CSTRING,0);
00472   if( p == NULL )return NULL;
00473   p->Size = StringSize;
00474   p->vType = VTYPE_STRING;
00475   return p;
00476   }
00477 
00478 
00479 
00480 
00481 
00482 
00483 
00484 int memory_SetRef(pMemoryObject pMo,
00485                    pFixSizeMemoryObject *ppVar,
00486                    pFixSizeMemoryObject *ppVal
00487   ){
00488 
00489 
00490 
00491   unsigned long refcount;
00492   pFixSizeMemoryObject *ppVAL;
00493   refcount = pMo->maxderef;
00494 
00495   
00496 
00497 
00498   while( ppVal && *ppVal && (*ppVal)->vType == VTYPE_REF && refcount ){
00499     ppVal = (*ppVal)->Value.aValue ;
00500     refcount --;
00501     }
00502 
00503   if( *ppVal && (*ppVal)->vType == VTYPE_REF )return COMMAND_ERROR_CIRCULAR;
00504 
00505   
00506 
00507 
00508 
00509   if( *ppVal == NULL ){
00510     *ppVal = memory_NewUndef(pMo);
00511     if( *ppVal == NULL )return COMMAND_ERROR_MEMORY_LOW;
00512     }
00513 
00514   ppVAL = ppVal;
00515   
00516   refcount = pMo->maxderef;
00517   while( (*ppVal)->link.rprev ){
00518     ppVal = (*ppVal)->link.rprev;
00519     if( ! refcount-- )return COMMAND_ERROR_CIRCULAR;
00520     }
00521   (*ppVal)->link.rprev = ppVar;
00522   (*ppVar)->next = *ppVal;
00523 
00524   
00525   refcount = pMo->maxderef;
00526   while( (*ppVar)->link.rprev ){
00527     (*ppVar)->Value.aValue = ppVAL;
00528     ppVar = (*ppVar)->link.rprev;
00529     if( ! refcount-- )return COMMAND_ERROR_CIRCULAR;
00530     }
00531   
00532   (*ppVar)->Value.aValue = ppVAL;
00533 
00534   return COMMAND_ERROR_SUCCESS;
00535   }
00536 
00537 
00538 
00539 
00540 
00541 pFixSizeMemoryObject memory_NewRef(pMemoryObject pMo
00542   ){
00543 
00544 
00545   pFixSizeMemoryObject p;
00546   p = memory_NewVariable(pMo,(BYTE)FIX_TYPE_LONG,0);
00547   if( p == NULL )return NULL;
00548   p->vType = VTYPE_REF;
00549   p->State = STATE_IMMORTAL;
00550   p->link.prev = p->next = NULL;
00551   p->Value.aValue = NULL;
00552   return p;
00553   }
00554 
00555 
00556 
00557 
00558 
00559 
00560 
00561 
00562 
00563 
00564 int memory_IsUndef(pFixSizeMemoryObject pVar
00565   ){
00566 
00567 
00568   if( pVar == NULL )return 1;
00569   if( pVar->vType == VTYPE_UNDEF )return 1;
00570   return 0;
00571   }
00572 
00573 
00574 
00575 
00576 
00577 
00578 
00579 
00580 
00581 
00582 
00583 int memory_Type(pFixSizeMemoryObject pVar
00584   ){
00585 
00586 
00587   if( pVar == NULL )return VTYPE_UNDEF;
00588   return pVar->vType;
00589   }
00590 
00591 
00592 
00593 
00594 
00595 pFixSizeMemoryObject memory_SelfOrRealUndef(pFixSizeMemoryObject pVar
00596   ){
00597 
00598 
00599   if( pVar == NULL )return NULL;
00600   if( pVar->vType == VTYPE_UNDEF )return NULL;
00601   return pVar;
00602   }
00603 
00604 
00605 
00606 
00607 
00608 pFixSizeMemoryObject memory_NewUndef(pMemoryObject pMo
00609   ){
00610 
00611 
00612   pFixSizeMemoryObject p;
00613   p = memory_NewVariable(pMo,(BYTE)FIX_TYPE_LONG,0);
00614   if( p == NULL )return NULL;
00615   p->vType = VTYPE_UNDEF;
00616   p->State = STATE_IMMORTAL;
00617   p->link.prev = p->next = NULL;
00618   p->Value.aValue = NULL;
00619   return p;
00620   }
00621 
00622 
00623 
00624 
00625 
00626 int memory_ReplaceVariable(pMemoryObject pMo,
00627                            pFixSizeMemoryObject *Lval,
00628                            pFixSizeMemoryObject NewValue,
00629                            pMortalList pMortal,
00630                            int iDupFlag
00631   ){
00632 
00633 
00634   int iErrorCode;
00635 
00636   iErrorCode = 0;
00637   
00638 
00639 
00640   if( memory_IsUndef(*Lval) && memory_IsUndef(NewValue) )return COMMAND_ERROR_SUCCESS;
00641 
00642   if( *Lval && NewValue ){
00643     if( NewValue->vType == VTYPE_LONG && (*Lval)->vType == VTYPE_LONG ){
00644       LONGVALUE(*Lval) = LONGVALUE(NewValue);
00645       return COMMAND_ERROR_SUCCESS;
00646       }
00647 
00648     if( NewValue->vType == VTYPE_DOUBLE && (*Lval)->vType == VTYPE_DOUBLE ){
00649       DOUBLEVALUE(*Lval) = DOUBLEVALUE(NewValue);
00650       return COMMAND_ERROR_SUCCESS;
00651       }
00652     }
00653 
00654   
00655   if( NewValue && iDupFlag ){
00656     NewValue = memory_DupMortalize(pMo,NewValue,pMortal,&iErrorCode);
00657     if( iErrorCode )return iErrorCode;
00658     }
00659 
00660 
00661   
00662   if( NewValue )
00663     
00664     memory_Immortalize(NewValue,pMortal);
00665 
00666   
00667 
00668   if( *Lval && (*Lval)->link.rprev && NewValue == NULL )NewValue = memory_NewUndef(pMo);
00669 
00670   
00671 
00672   if( *Lval && (*Lval)->link.rprev ){
00673     NewValue->link.rprev = (*Lval)->link.rprev;
00674     if( NewValue->link.rprev )(*(NewValue->link.rprev))->next = NewValue;
00675     (*Lval)->link.rprev = NULL;
00676     NewValue->next = (*Lval)->next;
00677     (*Lval)->next = NULL;
00678     }
00679   
00680   if( *Lval )memory_ReleaseVariable(pMo,*Lval);
00681 
00682   
00683   *Lval = NewValue;
00684 
00685   return COMMAND_ERROR_SUCCESS;
00686   }
00687 
00688 
00689 
00690 
00691 
00692 pFixSizeMemoryObject memory_NewLong(pMemoryObject pMo
00693   ){
00694 
00695 
00696   pFixSizeMemoryObject p;
00697   p = memory_NewVariable(pMo,(BYTE)FIX_TYPE_LONG,0);
00698   if( p == NULL )return NULL;
00699   p->vType = VTYPE_LONG;
00700   p->State = STATE_IMMORTAL;
00701   p->link.prev = p->next = NULL;
00702   return p;
00703   }
00704 
00705 
00706 
00707 
00708 
00709 pFixSizeMemoryObject memory_NewDouble(pMemoryObject pMo
00710   ){
00711 
00712 
00713   pFixSizeMemoryObject p;
00714   p = memory_NewVariable(pMo,FIX_TYPE_DOUBLE,0);
00715   if( p == NULL )return NULL;
00716   p->vType = VTYPE_DOUBLE;
00717   p->link.prev = p->next = NULL;
00718   p->State = STATE_IMMORTAL;
00719   return p;
00720   }
00721 
00722 
00723 
00724 
00725 
00726 pFixSizeMemoryObject memory_CopyArray(pMemoryObject pMo,
00727                                       pFixSizeMemoryObject p
00728   ){
00729 
00730 
00731   long aLow,aHigh;
00732   pFixSizeMemoryObject result;
00733   long i;
00734 
00735   if( p == NULL )return NULL;
00736   if( p->vType != VTYPE_ARRAY )return NULL;
00737   aLow = p->ArrayLowLimit;
00738   aHigh = p->ArrayHighLimit;
00739   result = memory_NewArray(pMo,aLow,aHigh);
00740   if( result == NULL )return NULL;
00741   for( i=0 ; i <= aHigh-aLow ; i++ ){
00742     if( memory_IsUndef(p->Value.aValue[i]) )continue;
00743     switch(p->Value.aValue[i]->vType ){
00744       case VTYPE_ARRAY :
00745         result->Value.aValue[i] = memory_CopyArray(pMo,p->Value.aValue[i]);
00746         if( result->Value.aValue[i] == NULL )return NULL;
00747         continue;
00748       case VTYPE_LONG:
00749         result->Value.aValue[i] = memory_NewLong(pMo);
00750         if( result->Value.aValue[i] == NULL )return NULL;
00751         result->Value.aValue[i]->Value.lValue = p->Value.aValue[i]->Value.lValue;
00752         continue;
00753       case VTYPE_DOUBLE:
00754         result->Value.aValue[i] = memory_NewDouble(pMo);
00755         if( result->Value.aValue[i] == NULL )return NULL;
00756         result->Value.aValue[i]->Value.dValue = p->Value.aValue[i]->Value.dValue;
00757         continue;
00758       case VTYPE_STRING:
00759         result->Value.aValue[i] = memory_NewString(pMo,STRLEN(p->Value.aValue[i]));
00760         if( result->Value.aValue[i] == NULL )return NULL;
00761         memcpy(result->Value.aValue[i]->Value.pValue,
00762                     p->Value.aValue[i]->Value.pValue,STRLEN(p->Value.aValue[i]));
00763         continue;
00764       case VTYPE_REF:
00765         result->Value.aValue[i] = memory_NewRef(pMo);
00766         memory_SetRef(pMo,&(result->Value.aValue[i]),&(p->Value.aValue[i]));
00767         continue;
00768       }
00769     }
00770   return result;
00771   }
00772 
00773 
00774 
00775 
00776 
00777 
00778 
00779 pFixSizeMemoryObject memory_NewArray(pMemoryObject pMo,
00780                                      long LowIndex,
00781                                      long HighIndex
00782   ){
00783 
00784 
00785 
00786 
00787   pFixSizeMemoryObject p;
00788   long i;
00789 
00790   p = memory_NewVariable(pMo,LARGE_BLOCK_TYPE, (HighIndex-LowIndex+1)*sizeof(void *));
00791   if( p == NULL )return NULL;
00792   p->vType = VTYPE_ARRAY;
00793   p->ArrayHighLimit = HighIndex;
00794   p->ArrayLowLimit = LowIndex;
00795   
00796   for( i=LowIndex ; i <= HighIndex ; i++ )
00797     p->Value.aValue[i - LowIndex] = NULL;
00798   p->link.prev = p->next = NULL;
00799   p->State = STATE_IMMORTAL;
00800   return p;
00801   }
00802 
00803 
00804 
00805 
00806 
00807 
00808 
00809 
00810 
00811 
00812 
00813 
00814 
00815 
00816 pFixSizeMemoryObject memory_ReDimArray(pMemoryObject pMo,
00817                                        pFixSizeMemoryObject p,
00818                                        long LowIndex,
00819                                        long HighIndex
00820   ){
00821 
00822 
00823   unsigned long NewSize;
00824   long i;
00825   pFixSizeMemoryObject *pValue;
00826 
00827   NewSize = (HighIndex-LowIndex+1)*sizeof(void*);
00828   if( NewSize > p->Size ){
00829     pValue = alloc_Alloc(NewSize,pMo->pMemorySegment);
00830     if( pValue == NULL )return NULL;
00831 
00832     for( i = LowIndex ; i<= HighIndex ; i++ )
00833       if( i < p->ArrayLowLimit || i > p->ArrayHighLimit )
00834         pValue[i-LowIndex] = NULL;
00835       else{
00836         pValue[i-LowIndex] = p->Value.aValue[i-p->ArrayLowLimit];
00837         
00838 
00839 
00840         if( p->Value.aValue[i-p->ArrayLowLimit] && 
00841             p->Value.aValue[i-p->ArrayLowLimit]->vType == VTYPE_REF &&
00842             (p->Value.aValue[i-p->ArrayLowLimit])->next )
00843           (p->Value.aValue[i-p->ArrayLowLimit])->next->link.rprev = pValue+i-LowIndex;
00844         }
00845 
00846     alloc_Free(p->Value.pValue,pMo->pMemorySegment);
00847     p->Value.aValue = pValue;
00848     p->ArrayHighLimit = HighIndex;
00849     p->ArrayLowLimit = LowIndex;
00850     return p;
00851     }
00852 
00853   pValue = p->Value.aValue;
00854   if( LowIndex < p->ArrayLowLimit )
00855     for( i = HighIndex ; i>= LowIndex ; i-- )
00856       if( i < p->ArrayLowLimit || i > p->ArrayHighLimit )
00857         pValue[i-LowIndex] = NULL;
00858       else{
00859         pValue[i-LowIndex] = pValue[i-p->ArrayLowLimit];
00860         
00861         if( p->Value.aValue[i-p->ArrayLowLimit]->vType == VTYPE_REF &&
00862             (p->Value.aValue[i-p->ArrayLowLimit])->next )
00863           (p->Value.aValue[i-p->ArrayLowLimit])->next->link.rprev = pValue+i-LowIndex;
00864         }
00865   else
00866     for( i = LowIndex ; i<= HighIndex ; i++ )
00867       if( i < p->ArrayLowLimit || i > p->ArrayHighLimit )
00868         pValue[i-LowIndex] = NULL;
00869       else{
00870         pValue[i-LowIndex] = pValue[i-p->ArrayLowLimit];
00871         
00872         if( p->Value.aValue[i-p->ArrayLowLimit]->vType == VTYPE_REF &&
00873             (p->Value.aValue[i-p->ArrayLowLimit])->next )
00874           (p->Value.aValue[i-p->ArrayLowLimit])->next->link.rprev = pValue+i-LowIndex;
00875         }
00876   p->ArrayHighLimit = HighIndex;
00877   p->ArrayLowLimit = LowIndex;
00878   return p;
00879   }
00880 
00881 
00882 
00883 
00884 
00885 
00886 
00887 
00888 
00889 
00890 
00891 
00892 pFixSizeMemoryObject memory_CheckArrayIndex(pMemoryObject pMo,
00893                                             pFixSizeMemoryObject p,
00894                                             long Index
00895   ){
00896 
00897 
00898 
00899   if( p->ArrayHighLimit < Index )
00900     return memory_ReDimArray(pMo,p,p->ArrayLowLimit,Index);
00901   if( p->ArrayLowLimit > Index )
00902     return memory_ReDimArray(pMo,p,Index,p->ArrayHighLimit);
00903   return p;
00904   }
00905 
00906 
00907 
00908 
00909 
00910 
00911 
00912 
00913 void memory_Mortalize(pFixSizeMemoryObject p,
00914                       pMortalList pMortal
00915   ){
00916 
00917 
00918 
00919 
00920 
00921 
00922   p->next = *pMortal;
00923   if( p->next )
00924     p->next->link.prev = p;
00925   p->link.prev = NULL;
00926   p->State = STATE_MORTAL;
00927   *pMortal = p;
00928   return;
00929   }
00930 
00931 
00932 
00933 
00934 
00935 
00936 
00937 
00938 
00939 
00940 void memory_Immortalize(pFixSizeMemoryObject p,
00941                         pMortalList pMortal
00942   ){
00943 
00944 
00945   if( ! p )return;
00946 
00947   if( p->State == STATE_IMMORTAL )return;
00948   if( p->link.prev )
00949     p->link.prev->next = p->next;
00950   else
00951     *pMortal = p->next;
00952 
00953   if( p->next )
00954     p->next->link.prev = p->link.prev;
00955 
00956   p->link.prev = NULL;
00957   p->next = NULL;
00958   p->State = STATE_IMMORTAL;
00959   return;
00960   }
00961 
00962 
00963 
00964 
00965 
00966 
00967 
00968 
00969 
00970 
00971 
00972 
00973 
00974 pFixSizeMemoryObject memory_NewMortal(pMemoryObject pMo,
00975                                       BYTE type,
00976                                       unsigned long LargeBlockSize,
00977                                       pMortalList pMortal
00978   ){
00979 
00980 
00981 
00982   pFixSizeMemoryObject p;
00983 
00984   p = memory_NewVariable(pMo,type,LargeBlockSize);
00985   if( p == NULL )return NULL;
00986   if( pMortal )
00987     memory_Mortalize(p,pMortal);
00988   return p;
00989   }
00990 
00991 
00992 
00993 
00994 
00995 
00996 
00997 
00998 
00999 pFixSizeMemoryObject memory_DupImmortal(pMemoryObject pMo,
01000                                         pFixSizeMemoryObject pVar,
01001                                         int *piErrorCode
01002   ){
01003 
01004 
01005   pFixSizeMemoryObject mypVar ;
01006   int i;
01007 
01008   *piErrorCode = MEM_ERROR_SUCCESS;
01009   if( pVar == NULL )return NULL;
01010 
01011   mypVar = memory_NewVariable(pMo,pVar->sType,pVar->Size);
01012   if( mypVar == NULL ){
01013     *piErrorCode = MEM_ERROR_MEMORY_LOW;
01014     return NULL;
01015     }
01016 
01017   mypVar->vType = pVar->vType;
01018   mypVar->Size  = pVar->Size;
01019   if( mypVar->vType == VTYPE_ARRAY ){
01020     mypVar->ArrayHighLimit = pVar->ArrayHighLimit;
01021     mypVar->ArrayLowLimit = pVar->ArrayLowLimit;
01022     for( i = 0 ; i <= mypVar->ArrayHighLimit - mypVar-> ArrayLowLimit ; i++ ){
01023       mypVar->Value.aValue[i] = memory_DupImmortal(pMo,pVar->Value.aValue[i],piErrorCode);
01024       if( *piErrorCode )return NULL;
01025       }
01026     }else{
01027     if( pVar->sType == LARGE_BLOCK_TYPE ){
01028       if( pVar->Size )
01029         memcpy(mypVar->Value.pValue, pVar->Value.pValue, mypVar->Size);
01030       }else{
01031       if( pVar->vType == VTYPE_STRING && pVar->sType != FIX_TYPE_CSTRING ){
01032         if( pVar->Size )
01033           memcpy(mypVar->Value.pValue,pVar->Value.pValue,mypVar->Size);
01034         }else{
01035         mypVar->Value = pVar->Value;
01036         }
01037       }
01038     }
01039   return mypVar;
01040   }
01041 
01042 
01043 
01044 
01045 
01046 
01047 
01048 
01049 pFixSizeMemoryObject memory_DupVar(pMemoryObject pMo,
01050                                    pFixSizeMemoryObject pVar,
01051                                    pMortalList pMyMortal,
01052                                    int *piErrorCode
01053   ){
01054 
01055 
01056 
01057 
01058 
01059 
01060 
01061 
01062 
01063 
01064 
01065 
01066 
01067 
01068 
01069 
01070 
01071   pFixSizeMemoryObject mypVar ;
01072 
01073   *piErrorCode = MEM_ERROR_SUCCESS;
01074   if( pVar == NULL )return NULL;
01075 
01076   if( pVar->vType == VTYPE_ARRAY ){
01077     *piErrorCode = MEM_ERROR_INTERNAL001;
01078     return NULL;
01079     }
01080 
01081   mypVar = memory_NewMortal(pMo,pVar->sType,pVar->Size,pMyMortal);
01082   if( mypVar == NULL ){
01083     *piErrorCode = MEM_ERROR_MEMORY_LOW;
01084     return NULL;
01085     }
01086 
01087   mypVar->vType = pVar->vType;
01088   mypVar->Size  = pVar->Size;
01089   if( pVar->sType == LARGE_BLOCK_TYPE ){
01090     if( pVar->Size )
01091       memcpy(mypVar->Value.pValue, pVar->Value.pValue, mypVar->Size);
01092     }else{
01093     if( pVar->vType == VTYPE_STRING && pVar->sType != FIX_TYPE_CSTRING ){
01094       if( pVar->Size )
01095         memcpy(mypVar->Value.pValue,pVar->Value.pValue,mypVar->Size);
01096       }else{
01097       memcpy(&(mypVar->Value),&(pVar->Value),sizeof(union _fsmoval));
01098       }
01099     }
01100   return mypVar;
01101   }
01102 
01103 
01104 
01105 
01106 
01107 
01108 
01109 
01110 
01111 pFixSizeMemoryObject memory_DupMortalize(pMemoryObject pMo,
01112                                          pFixSizeMemoryObject pVar,
01113                                          pMortalList pMyMortal,
01114                                          int *piErrorCode
01115   ){
01116 
01117 
01118 
01119   if( *piErrorCode )return NULL;
01120   if( pVar && IsMortal(pVar) )return pVar;
01121   return memory_DupVar(pMo,pVar,pMyMortal,piErrorCode);
01122   }
01123 
01124 
01125 
01126 
01127 
01128 
01129 
01130 
01131 
01132 
01133 
01134 
01135 
01136 void memory_ReleaseMortals(pMemoryObject pMo,
01137                            pMortalList pMortal
01138   ){
01139 
01140 
01141   MortalList p;
01142 
01143   if( pMortal == NULL )return; 
01144   while( p=*pMortal ){
01145     *pMortal = p->next;
01146     memory_ReleaseVariable(pMo,p);
01147     }
01148   *pMortal = NULL;
01149   }
01150 
01151 #ifdef _DEBUG
01152 
01153 
01154 
01155 
01156 
01157 
01158 
01159 
01160 
01161 void memory_DebugDumpVariable(pMemoryObject pMo,
01162                               pFixSizeMemoryObject pVar
01163   ){
01164 
01165 
01166   long i;
01167 
01168   if( pVar == NULL ){
01169     printf("real undef");
01170     return;
01171     }
01172 
01173   switch( pVar->vType ){
01174     case VTYPE_UNDEF:
01175       printf("ref undef");
01176       return;
01177 
01178     case VTYPE_STRING:
01179       printf("string(%d)[",STRLEN(pVar));
01180       for( i=0 ;  ((unsigned long)i) < STRLEN(pVar) ; i++ ){
01181         printf("%c",STRINGVALUE(pVar)[i]);
01182         }
01183       printf("]");
01184       return;
01185 
01186     case VTYPE_LONG:
01187       printf("long[%d]",LONGVALUE(pVar));
01188       return;
01189 
01190     case VTYPE_DOUBLE:
01191       printf("long[%f]",DOUBLEVALUE(pVar));
01192       return;
01193 
01194     case VTYPE_ARRAY:
01195       printf("ARRAY(%d,%d)\n[",pVar->ArrayLowLimit, pVar->ArrayHighLimit);
01196       for( i=pVar->ArrayLowLimit ; i <= pVar->ArrayHighLimit  ; i++ ){
01197         memory_DebugDumpVariable(pMo,pVar->Value.aValue[i-pVar->ArrayLowLimit]);
01198         }
01199       printf(" ]");
01200       return;
01201 
01202     case VTYPE_REF:
01203       printf("->");
01204       memory_DebugDumpVariable(pMo,*(pVar->Value.aValue));
01205       return;
01206     }
01207 
01208   }
01209 
01210 
01211 
01212 
01213 
01214 
01215 
01216 
01217 
01218 
01219 void memory_DebugDumpMortals(pMemoryObject pMo,
01220                              pMortalList pMortal
01221   ){
01222 
01223 
01224   MortalList p,q;
01225   long i;
01226 
01227   if( pMortal == NULL ){
01228     printf("This mortal list is empty\n");
01229     return; 
01230     }
01231 
01232   printf("Mortal list %p:\n",pMortal);
01233   i = 1;
01234   q = *pMortal;
01235   while( p = q ){
01236     q = p->next;
01237     printf("%d. ",i++);
01238     memory_DebugDumpVariable(pMo,p);
01239     printf("\n");
01240     }
01241   }
01242 #endif
01243 
01244 
01245 
01246 
01247 
01248 pFixSizeMemoryObject memory_NewMortalString(pMemoryObject pMo,
01249                                             unsigned long StringSize,
01250                                             pMortalList pMortal
01251   ){
01252 
01253 
01254 
01255   pFixSizeMemoryObject p;
01256 
01257   p = memory_NewString(pMo,StringSize);
01258   if( p == NULL )return NULL;
01259   if( pMortal )
01260     memory_Mortalize(p,pMortal);
01261   return p;
01262   }
01263 
01264 
01265 
01266 
01267 
01268 pFixSizeMemoryObject memory_NewMortalCString(pMemoryObject pMo,
01269                                              unsigned long StringSize,
01270                                              pMortalList pMortal
01271   ){
01272 
01273 
01274 
01275   pFixSizeMemoryObject p;
01276 
01277   p = memory_NewCString(pMo,StringSize);
01278   if( p == NULL )return NULL;
01279   if( pMortal )
01280     memory_Mortalize(p,pMortal);
01281   return p;
01282   }
01283 
01284 
01285 
01286 
01287 
01288 pFixSizeMemoryObject memory_NewMortalLong(pMemoryObject pMo,
01289                                             pMortalList pMortal
01290   ){
01291 
01292 
01293 
01294   pFixSizeMemoryObject p;
01295 
01296   p = memory_NewLong(pMo);
01297   if( p == NULL )return NULL;
01298   if( pMortal )
01299     memory_Mortalize(p,pMortal);
01300   return p;
01301   }
01302 
01303 
01304 
01305 
01306 
01307 
01308 
01309 
01310 
01311 
01312 
01313 
01314 pFixSizeMemoryObject memory_NewMortalRef(pMemoryObject pMo,
01315                                          pMortalList pMortal
01316   ){
01317 
01318 
01319 
01320 
01321   
01322   if( pMortal == NULL )return memory_NewRef(pMo);
01323   return NULL;
01324 #if 0
01325   
01326   pFixSizeMemoryObject p;
01327   p = memory_NewRef(pMo);
01328   if( p == NULL )return NULL;
01329   if( pMortal )
01330     memory_Mortalize(p,pMortal);
01331   return p;
01332 #endif
01333   }
01334 
01335 
01336 
01337 
01338 
01339 
01340 pFixSizeMemoryObject memory_NewMortalDouble(pMemoryObject pMo,
01341                                             pMortalList pMortal
01342   ){
01343 
01344 
01345 
01346   pFixSizeMemoryObject p;
01347 
01348   p = memory_NewDouble(pMo);
01349   if( p == NULL )return NULL;
01350   if( pMortal )
01351     memory_Mortalize(p,pMortal);
01352   return p;
01353   }
01354 
01355 
01356 
01357 
01358 
01359 
01360 pFixSizeMemoryObject memory_NewMortalArray(pMemoryObject pMo,
01361                                            pMortalList pMortal,
01362                                            long IndexLow,
01363                                            long IndexHigh
01364   ){
01365 
01366 
01367 
01368   pFixSizeMemoryObject p;
01369 
01370   p = memory_NewArray(pMo,IndexLow,IndexHigh);
01371   if( p == NULL )return NULL;
01372   if( pMortal )
01373     memory_Mortalize(p,pMortal);
01374   return p;
01375   }