Annotation of parser3/src/include/pa_memory.h, revision 1.1.2.9.2.16

1.1.2.1   paf         1: /** @file
                      2:        Parser: memory reference counting classes decls.
                      3: 
                      4:        Copyright (c) 2001-2003 ArtLebedev Group (http://www.artlebedev.com)
                      5: 
                      6:        Author: Alexandr Petrosian <paf@design.ru> (http://paf.design.ru)
                      7: */
                      8: 
                      9: #ifndef PA_MEMORY_H
                     10: #define PA_MEMORY_H
                     11: 
1.1.2.9.2.16! paf        12: static const char* IDENT_MEMORY_H="$Date: 2003/03/27 14:05:40 $";
1.1.2.1   paf        13: 
                     14: // include
                     15: 
                     16: #include "pa_config_includes.h"
1.1.2.9.2.15  paf        17: 
1.1.2.9.2.1  paf        18: #include "gc.h"
                     19: 
1.1.2.1   paf        20: 
                     21: #ifdef XML
                     22: #      include "gdome.h"
                     23: // for xmlChar
                     24: #      include "libxml/tree.h"
                     25: #endif
                     26: 
1.1.2.9.2.16! paf        27: // defines
        !            28: 
        !            29: #define PA_DEBUG_GC_MEMORY
        !            30: 
        !            31: #ifdef PA_DEBUG_GC_MEMORY
        !            32: void* pa_gc_malloc(size_t size);
        !            33: void* pa_gc_malloc_atomic(size_t size);
        !            34: void* pa_gc_realloc(void* ptr, size_t size);
        !            35: void pa_gc_free(void* ptr);
        !            36: 
        !            37: #      define PA_GC_MALLOC(size) pa_gc_malloc(size)
        !            38: #      define PA_GC_MALLOC_ATOMIC(size) pa_gc_malloc_atomic(size)
        !            39: #      define PA_GC_REALLOC(ptr,size) pa_gc_realloc(ptr,size)
        !            40: #      define PA_GC_FREE(ptr) pa_gc_free(ptr)
        !            41: #else
        !            42: inline void* pa_gc_malloc(size_t size) { return GC_MALLOC(size); }
        !            43: inline void* pa_gc_malloc_atomic(size_t size) { return GC_MALLOC_ATOMIC(size); }
        !            44: inline void* pa_gc_realloc(void* ptr, size_t size) { return GC_REALLOC(ptr, size); }
        !            45: inline void pa_gc_free(void* ptr) { GC_FREE(ptr); }
        !            46: 
        !            47: #      define PA_GC_MALLOC(size) pa_gc_malloc(size)
        !            48: #      define PA_GC_MALLOC_ATOMIC(size) pa_gc_malloc_atomic(size)
        !            49: #      define PA_GC_REALLOC(ptr,size) pa_gc_realloc(ptr,size)
        !            50: #      define PA_GC_FREE(ptr) pa_gc_free(ptr)
        !            51: #endif
        !            52: 
        !            53: 
1.1.2.1   paf        54: // forwards
                     55: 
1.1.2.9.2.5  paf        56: void *pa_fail_alloc(const char* what, size_t size);
1.1.2.2   paf        57: 
                     58: // inlines
                     59: 
                     60: inline void *pa_malloc(size_t size) {
1.1.2.9.2.16! paf        61:        if(void *result=PA_GC_MALLOC(size))
1.1.2.2   paf        62:                return result;
                     63: 
                     64:        return pa_fail_alloc("allocate", size);
                     65: }
                     66: 
1.1.2.9.2.1  paf        67: inline void *pa_malloc_atomic(size_t size) {
1.1.2.9.2.16! paf        68:        if(void *result=PA_GC_MALLOC_ATOMIC(size))
1.1.2.2   paf        69:                return result;
                     70: 
                     71:        return pa_fail_alloc("allocate clean", size);
                     72: }
1.1.2.9.2.4  paf        73: /// @a length may be null, which mean "autocalc it"
1.1.2.9.2.5  paf        74: inline char *pa_strdup(const char* auto_variable_never_null, size_t length=0) {
1.1.2.9.2.4  paf        75:        if(!length)
                     76:                length=strlen(auto_variable_never_null);
1.1.2.9.2.7  paf        77: 
                     78:        size_t size=length+1;
1.1.2.9.2.16! paf        79:        if(char *result=static_cast<char*>(PA_GC_MALLOC_ATOMIC(size))) {
1.1.2.9.2.7  paf        80:                memcpy(result, auto_variable_never_null, length);
                     81:                result[length]=0;
1.1.2.9.2.4  paf        82:                return result;
                     83:        }
                     84: 
                     85:        return static_cast<char*>(pa_fail_alloc("allocate clean", size));
                     86: }
1.1.2.9.2.10  paf        87: 
1.1.2.2   paf        88: inline void pa_free(void *ptr) {
1.1.2.9.2.16! paf        89:        PA_GC_FREE(ptr);
1.1.2.2   paf        90: }
                     91: 
                     92: inline void *pa_realloc(void *ptr, size_t size) {
1.1.2.9.2.16! paf        93:        if(void *result=PA_GC_REALLOC(ptr, size))
1.1.2.2   paf        94:                return result;
                     95: 
                     96:        return pa_fail_alloc("reallocate to", size);
                     97: }
1.1.2.1   paf        98: 
1.1.2.9.2.4  paf        99: //{@ these operators are disabled, one should explicitely specify either new(UseGC) or new(PointerFreeGC)
1.1.2.9.2.6  paf       100: inline void *operator new(size_t size) { abort(); } // disabled
                    101: inline void *operator new[] (size_t size) { abort(); } // disabled
1.1.2.9.2.4  paf       102: //}@
1.1.2.9.2.3  paf       103: 
                    104: #define UseGC ((int)1)
                    105: #define PointerFreeGC (true)
                    106: 
1.1.2.9.2.14  paf       107: //{@ Array-oriented
1.1.2.9.2.15  paf       108: inline void *operator new[] (size_t size, int mode) { // UseGC
1.1.2.9.2.3  paf       109:        return pa_malloc(size);
                    110: }
                    111: inline void *operator new[] (size_t size, bool) { // PointerFreeGC
1.1.2.9.2.1  paf       112:        return pa_malloc_atomic(size);
1.1.2.1   paf       113: }
                    114: inline void operator delete[] (void *ptr) {
                    115:        pa_free(ptr);
                    116: }
1.1.2.9.2.14  paf       117: //}@
                    118: 
                    119: //{@ Structure-oriented
                    120: inline void *operator new (size_t size, int) { // UseGC
                    121:        return pa_malloc(size);
                    122: }
                    123: inline void *operator new (size_t size, bool) { // PointerFreeGC
                    124:        return pa_malloc_atomic(size);
                    125: }
                    126: inline void operator delete(void *ptr) {
                    127:        pa_free(ptr);
                    128: }
                    129: //}@
1.1.2.1   paf       130: 
1.1.2.9.2.1  paf       131: /// memory allocation/dallocation goes via pa_malloc/pa_free.
1.1.2.1   paf       132: class PA_Allocated {
                    133: public:
                    134:        /// the sole: instances allocated using our functions
                    135:        static void *operator new(size_t size) { 
                    136:                return pa_malloc(size);
                    137:        }
                    138:        static void operator delete(void *ptr) {
                    139:                pa_free(ptr);
                    140:        }
                    141:        static void *malloc(size_t size) {
                    142:                return pa_malloc(size);
                    143:        }
1.1.2.9.2.1  paf       144:        static void *malloc_atomic(size_t size) {
                    145:                return pa_malloc_atomic(size);
1.1.2.9.2.8  paf       146:        }
                    147:        static char *strdup(const char* auto_variable_never_null, size_t length=0) {
                    148:                return pa_strdup(auto_variable_never_null, length);
1.1.2.1   paf       149:        }
                    150:        static void free(void *ptr) {
                    151:                pa_free(ptr);
                    152:        }
                    153:        static void *realloc(void *ptr, size_t size) {
                    154:                return pa_realloc(ptr, size);
                    155:        }
1.1.2.9.2.2  paf       156: 
                    157: private: // disabled from accidental use
                    158: 
1.1.2.9.2.9  paf       159:        /// use malloc/malloc_atomic instead [GC clears result of those]
1.1.2.9.2.2  paf       160:        static void *calloc(size_t size);
1.1.2.9.2.13  paf       161: 
                    162: };
                    163: 
                    164: /// Those who want their destructor called during finalization, must derive from this class [also]
                    165: class PA_Cleaned {
1.1.2.9.2.15  paf       166: #ifndef PA_DEBUG_DISABLE_GC
1.1.2.9.2.13  paf       167:        static void cleanup( void* obj, void* displ ) {
                    168:            ((PA_Cleaned*) ((char*) obj + (ptrdiff_t) displ))->~PA_Cleaned();
                    169:        }
                    170: 
                    171: public:
                    172:        PA_Cleaned() {
                    173:                GC_finalization_proc oldProc;
                    174:                void* oldData;
                    175:                void* base = GC_base( (void *) this );
                    176:                if (0 != base)  {
                    177:                        // Don't call the debug version, since this is a real base address.
                    178:                        GC_register_finalizer_ignore_self( 
                    179:                                base, (GC_finalization_proc)cleanup, (void*) ((char*) this - (char*) base), 
                    180:                                &oldProc, &oldData );
                    181:                        if (0 != oldProc) {
                    182:                                GC_register_finalizer_ignore_self( base, oldProc, oldData, 0, 0 );
                    183:                        }
                    184:                }
                    185:        }
                    186: 
                    187:        virtual ~PA_Cleaned() {
                    188:            GC_REGISTER_FINALIZER_IGNORE_SELF( GC_base(this), 0, 0, 0, 0 );
                    189:        }
1.1.2.9.2.15  paf       190: #endif
1.1.2.1   paf       191: };
                    192: 
1.1.2.9.2.1  paf       193: /// Base for all Parser classes
                    194: typedef PA_Allocated PA_Object;
1.1.2.1   paf       195: 
1.1.2.9.2.6  paf       196: // defines
                    197: 
                    198: #define override
                    199: #define rethrow throw
1.1.2.9.2.10  paf       200: 
1.1.2.1   paf       201: 
                    202: #endif

E-mail: