Diff for /parser3/src/main/pa_memory.C between versions 1.1.2.5.2.13 and 1.23

version 1.1.2.5.2.13, 2003/07/22 08:19:24 version 1.23, 2025/08/01 17:10:14
Line 1 Line 1
 /** @file  /** @file
         Parser: memory reference counting classes.          Parser: memory reference counting classes.
   
         Copyright (c) 2001-2003 ArtLebedev Group (http://www.artlebedev.com)          Copyright (c) 2001-2024 Art. Lebedev Studio (http://www.artlebedev.com)
         Author: Alexandr Petrosian <paf@design.ru> (http://paf.design.ru)          Authors: Konstantin Morshnev <moko@design.ru>, Alexandr Petrosian <paf@design.ru>
 */  */
   
 static const char* IDENT_MEMORY_C="$Date$";  
   
 #include "pa_sapi.h"  #include "pa_sapi.h"
 #include "pa_common.h"  #include "pa_common.h"
   #include "pa_threads.h"
   
   volatile const char * IDENT_PA_MEMORY_C="$Id$" IDENT_PA_MEMORY_H;
   
 void *pa_fail_alloc(const char* what, size_t size) {  void *pa_fail_alloc(const char* what, size_t size) {
 #ifdef PA_DEBUG_DISABLE_GC  #ifdef PA_DEBUG_DISABLE_GC
         SAPI::die("out of memory (in pa_fail_alloc)");          SAPI::die("out of memory (in pa_fail_alloc)");
 #else  #else
         SAPI::die("out of memory: failed to %s %u bytes. "          SAPI::die("out of memory: failed to %s %u bytes. heap_used=%u, heap_free=%u, bytes_since_gc=%u, total_bytes=%u",
                 "heap_used=%lu, heap_free=%lu, bytes_since_gc=%lu, total_bytes=%lu",                  what, size, GC_get_heap_size(), GC_get_free_bytes(), GC_get_bytes_since_gc(), GC_get_total_bytes());
                 what, size,  
                 GC_get_heap_size(),  
                 GC_get_free_bytes(),  
                 GC_get_bytes_since_gc(),  
                 GC_get_total_bytes()  
                 );  
 #endif  #endif
         // never reached          // never reached
         return 0;          return 0;
 }  }
   
   #ifndef PA_DEBUG_DISABLE_GC
 #ifdef PA_DEBUG_GC_MEMORY  // Under Windows pa_fail_alloc was referenced in function GC_default_on_abort in gc.lib(misc.c) and thus should be extern "C"
   extern "C" void *pa_fail_alloc(const char* what) {
 const size_t HEADTAIL_SIZE=4;          SAPI::die("fatal memory error: %s. heap_used=%u, heap_free=%u, bytes_since_gc=%u, total_bytes=%u",
                   what ? what : "pre-exit", GC_get_heap_size(), GC_get_free_bytes(), GC_get_bytes_since_gc(), GC_get_total_bytes());
 static size_t debug_size(size_t user_size) {          // never reached
         return user_size+HEADTAIL_SIZE*2;          return 0;
 }  
   
 const int BEFORE_MARK=0xBEF0BEF0;  
 const int AFTER_MARK=0xAFEEAFEE;  
 const char PAD_MARK='\xAD';  
   
 static void* fill_return_user(void* aptr, size_t pure_size) {  
         char* ptr=(char*)aptr;  
         memcpy(ptr, &BEFORE_MARK, HEADTAIL_SIZE);  
         memcpy(ptr+pure_size-HEADTAIL_SIZE, &AFTER_MARK, HEADTAIL_SIZE);  
   
         // pAD  
         size_t raw_size=GC_size(aptr);  
         for(size_t i=pure_size; i<raw_size; i++)  
                 ptr[i]=PAD_MARK;  
   
         //if(ptr>=(char*)0x01c357e40 && ptr<=((char*)0x01c357e4+100))  
                 //printf("valid:0x%p\n", ptr);  
   
         return ptr+HEADTAIL_SIZE;  
 }  
 static void* check_return_debug(void* auser_ptr) {  
         char* user_ptr=(char*)auser_ptr;  
         char* ptr=user_ptr-HEADTAIL_SIZE;  
   
         size_t raw_size=GC_size(ptr);  
         assert(raw_size!=0);  
   
         size_t pure_size=raw_size;  
         while(ptr[pure_size-1]==PAD_MARK)  
                 pure_size--;  
   
         assert(memcmp(ptr, &BEFORE_MARK, HEADTAIL_SIZE)==0);  
         assert(memcmp(ptr+pure_size-HEADTAIL_SIZE, &AFTER_MARK, HEADTAIL_SIZE)==0);  
   
         return ptr;  
 }  
   
   
 void* pa_gc_malloc(size_t size) {  
         size=debug_size(size);  
         return fill_return_user(GC_MALLOC(size), size);  
 }  
   
 void* pa_gc_malloc_atomic(size_t size) {  
         size=debug_size(size);  
         return fill_return_user(GC_MALLOC_ATOMIC(size), size);  
 }  }
   #endif
   
 void* pa_gc_realloc(void* user_ptr, size_t size) {  int pa_free_space_divisor = 0;
         GC_is_visible(user_ptr);  
   
         //printf("realloc: 0x%p -> %u\n", ptr, size);  void pa_gc_collect(bool forced){
         size=debug_size(size);  #ifndef PA_DEBUG_DISABLE_GC
         return fill_return_user(      int divisor = pa_free_space_divisor; // as it can change during collect in multithreaded enviroment
                 GC_realloc(      if(!divisor) GC_enable();
                         check_return_debug(user_ptr),       if(!divisor || forced) GC_gcollect();
                         size),      if(!divisor) GC_disable();
                 size);  #endif
 }  
 void pa_gc_free(void* ptr) {  
         // ignore free  
 }  }
   
   void pa_gc_set_free_space_divisor(int divisor){
   #ifndef PA_DEBUG_DISABLE_GC
           if(divisor != pa_free_space_divisor){
                   SYNCHRONIZED;
                   if(pa_free_space_divisor){
                           if(!divisor) GC_disable();
                   } else {
                           if(divisor) GC_enable();
                   }
                   if(divisor)
                           GC_set_free_space_divisor(divisor);
                   pa_free_space_divisor = divisor;
           }
 #endif  #endif
   }

Removed from v.1.1.2.5.2.13  
changed lines
  Added in v.1.23


E-mail: