Back to index

lightning-sunbird  0.9+nobinonly
pcr_interface.c
Go to the documentation of this file.
00001 /* 
00002  * Copyright (c) 1991-1994 by Xerox Corporation.  All rights reserved.
00003  *
00004  * THIS MATERIAL IS PROVIDED AS IS, WITH ABSOLUTELY NO WARRANTY EXPRESSED
00005  * OR IMPLIED.  ANY USE IS AT YOUR OWN RISK.
00006  *
00007  * Permission is hereby granted to use or copy this program
00008  * for any purpose,  provided the above notices are retained on all copies.
00009  * Permission to modify the code and to distribute modified code is granted,
00010  * provided the above notices are retained, and a notice that the code was
00011  * modified is included with the above copyright notice.
00012  */
00013 /* Boehm, February 7, 1996 11:09 am PST */
00014 # include "gc_priv.h"
00015 
00016 # ifdef PCR
00017 /*
00018  * Note that POSIX PCR requires an ANSI C compiler.  Hence we are allowed
00019  * to make the same assumption here.
00020  * We wrap all of the allocator functions to avoid questions of
00021  * compatibility between the prototyped and nonprototyped versions of the f
00022  */
00023 # include "config/PCR_StdTypes.h"
00024 # include "mm/PCR_MM.h"
00025 # include <errno.h>
00026 
00027 # define MY_MAGIC 17L
00028 # define MY_DEBUGMAGIC 42L
00029 
00030 void * GC_AllocProc(size_t size, PCR_Bool ptrFree, PCR_Bool clear )
00031 {
00032     if (ptrFree) {
00033         void * result = (void *)GC_malloc_atomic(size);
00034         if (clear && result != 0) BZERO(result, size);
00035         return(result);
00036     } else {
00037         return((void *)GC_malloc(size));
00038     }
00039 }
00040 
00041 void * GC_DebugAllocProc(size_t size, PCR_Bool ptrFree, PCR_Bool clear )
00042 {
00043     if (ptrFree) {
00044         void * result = (void *)GC_debug_malloc_atomic(size, __FILE__,
00045                                                       __LINE__);
00046         if (clear && result != 0) BZERO(result, size);
00047         return(result);
00048     } else {
00049         return((void *)GC_debug_malloc(size, __FILE__, __LINE__));
00050     }
00051 }
00052 
00053 # define GC_ReallocProc GC_realloc
00054 void * GC_DebugReallocProc(void * old_object, size_t new_size_in_bytes)
00055 {
00056     return(GC_debug_realloc(old_object, new_size_in_bytes, __FILE__, __LINE__));
00057 }
00058 
00059 # define GC_FreeProc GC_free
00060 # define GC_DebugFreeProc GC_debug_free
00061 
00062 typedef struct {
00063   PCR_ERes (*ed_proc)(void *p, size_t size, PCR_Any data);
00064   GC_bool ed_pointerfree;
00065   PCR_ERes ed_fail_code;
00066   PCR_Any ed_client_data;
00067 } enumerate_data;
00068 
00069 void GC_enumerate_block(h, ed)
00070 register struct hblk *h;
00071 enumerate_data * ed;
00072 {
00073     register hdr * hhdr;
00074     register int sz;
00075     word *p;
00076     word * lim;
00077     
00078     hhdr = HDR(h);
00079     sz = hhdr -> hb_sz;
00080     if (sz >= 0 && ed -> ed_pointerfree
00081        || sz <= 0 && !(ed -> ed_pointerfree)) return;
00082     if (sz < 0) sz = -sz;
00083     lim = (word *)(h+1) - sz;
00084     p = (word *)h;
00085     do {
00086         if (PCR_ERes_IsErr(ed -> ed_fail_code)) return;
00087         ed -> ed_fail_code =
00088             (*(ed -> ed_proc))(p, WORDS_TO_BYTES(sz), ed -> ed_client_data);
00089         p+= sz;
00090     } while (p <= lim);
00091 }
00092 
00093 struct PCR_MM_ProcsRep * GC_old_allocator = 0;
00094 
00095 PCR_ERes GC_EnumerateProc(
00096     PCR_Bool ptrFree,
00097     PCR_ERes (*proc)(void *p, size_t size, PCR_Any data),
00098     PCR_Any data
00099 )
00100 {
00101     enumerate_data ed;
00102     
00103     ed.ed_proc = proc;
00104     ed.ed_pointerfree = ptrFree;
00105     ed.ed_fail_code = PCR_ERes_okay;
00106     ed.ed_client_data = data;
00107     GC_apply_to_all_blocks(GC_enumerate_block, &ed);
00108     if (ed.ed_fail_code != PCR_ERes_okay) {
00109         return(ed.ed_fail_code);
00110     } else {
00111        /* Also enumerate objects allocated by my predecessors */
00112        return((*(GC_old_allocator->mmp_enumerate))(ptrFree, proc, data));
00113     }
00114 }
00115 
00116 void GC_DummyFreeProc(void *p) {}
00117 
00118 void GC_DummyShutdownProc(void) {}
00119 
00120 struct PCR_MM_ProcsRep GC_Rep = {
00121        MY_MAGIC,
00122        GC_AllocProc,
00123        GC_ReallocProc,
00124        GC_DummyFreeProc,    /* mmp_free */
00125        GC_FreeProc,                /* mmp_unsafeFree */
00126        GC_EnumerateProc,
00127        GC_DummyShutdownProc /* mmp_shutdown */
00128 };
00129 
00130 struct PCR_MM_ProcsRep GC_DebugRep = {
00131        MY_DEBUGMAGIC,
00132        GC_DebugAllocProc,
00133        GC_DebugReallocProc,
00134        GC_DummyFreeProc,    /* mmp_free */
00135        GC_DebugFreeProc,           /* mmp_unsafeFree */
00136        GC_EnumerateProc,
00137        GC_DummyShutdownProc /* mmp_shutdown */
00138 };
00139 
00140 GC_bool GC_use_debug = 0;
00141 
00142 void GC_pcr_install()
00143 {
00144     PCR_MM_Install((GC_use_debug? &GC_DebugRep : &GC_Rep), &GC_old_allocator);
00145 }
00146 
00147 PCR_ERes
00148 PCR_GC_Setup(void)
00149 {
00150     return PCR_ERes_okay;
00151 }
00152 
00153 PCR_ERes
00154 PCR_GC_Run(void)
00155 {
00156 
00157     if( !PCR_Base_TestPCRArg("-nogc") ) {
00158         GC_quiet = ( PCR_Base_TestPCRArg("-gctrace") ? 0 : 1 );
00159         GC_use_debug = (GC_bool)PCR_Base_TestPCRArg("-debug_alloc");
00160         GC_init();
00161         if( !PCR_Base_TestPCRArg("-nogc_incremental") ) {
00162             /*
00163              * awful hack to test whether VD is implemented ...
00164              */
00165             if( PCR_VD_Start( 0, NIL, 0) != PCR_ERes_FromErr(ENOSYS) ) {
00166                GC_enable_incremental();
00167            }
00168        }
00169     }
00170     return PCR_ERes_okay;
00171 }
00172 
00173 # endif