[BACK]Return to new_hblk.c CVS log [TXT][DIR] Up to [local] / OpenXM_contrib2 / asir2000 / gc

Annotation of OpenXM_contrib2/asir2000/gc/new_hblk.c, Revision 1.3

1.1       noro        1: /*
                      2:  * Copyright 1988, 1989 Hans-J. Boehm, Alan J. Demers
                      3:  * Copyright (c) 1991-1994 by Xerox Corporation.  All rights reserved.
1.3     ! noro        4:  * Copyright (c) 2000 by Hewlett-Packard Company.  All rights reserved.
1.1       noro        5:  *
                      6:  * THIS MATERIAL IS PROVIDED AS IS, WITH ABSOLUTELY NO WARRANTY EXPRESSED
                      7:  * OR IMPLIED.  ANY USE IS AT YOUR OWN RISK.
                      8:  *
                      9:  * Permission is hereby granted to use or copy this program
                     10:  * for any purpose,  provided the above notices are retained on all copies.
                     11:  * Permission to modify the code and to distribute modified code is granted,
                     12:  * provided the above notices are retained, and a notice that the code was
                     13:  * modified is included with the above copyright notice.
                     14:  *
                     15:  * This file contains the functions:
                     16:  *     ptr_t GC_build_flXXX(h, old_fl)
                     17:  *     void GC_new_hblk(n)
                     18:  */
                     19: /* Boehm, May 19, 1994 2:09 pm PDT */
                     20:
                     21:
                     22: # include <stdio.h>
1.3     ! noro       23: # include "private/gc_priv.h"
1.1       noro       24:
                     25: #ifndef SMALL_CONFIG
                     26: /*
                     27:  * Build a free list for size 1 objects inside hblk h.  Set the last link to
                     28:  * be ofl.  Return a pointer tpo the first free list entry.
                     29:  */
                     30: ptr_t GC_build_fl1(h, ofl)
                     31: struct hblk *h;
                     32: ptr_t ofl;
                     33: {
1.3     ! noro       34:     register word * p = h -> hb_body;
1.1       noro       35:     register word * lim = (word *)(h + 1);
                     36:
                     37:     p[0] = (word)ofl;
                     38:     p[1] = (word)(p);
                     39:     p[2] = (word)(p+1);
                     40:     p[3] = (word)(p+2);
                     41:     p += 4;
                     42:     for (; p < lim; p += 4) {
                     43:         p[0] = (word)(p-1);
                     44:         p[1] = (word)(p);
                     45:         p[2] = (word)(p+1);
                     46:         p[3] = (word)(p+2);
                     47:     };
                     48:     return((ptr_t)(p-1));
                     49: }
                     50:
                     51: /* The same for size 2 cleared objects */
                     52: ptr_t GC_build_fl_clear2(h, ofl)
                     53: struct hblk *h;
                     54: ptr_t ofl;
                     55: {
1.3     ! noro       56:     register word * p = h -> hb_body;
1.1       noro       57:     register word * lim = (word *)(h + 1);
                     58:
                     59:     p[0] = (word)ofl;
                     60:     p[1] = 0;
                     61:     p[2] = (word)p;
                     62:     p[3] = 0;
                     63:     p += 4;
                     64:     for (; p < lim; p += 4) {
                     65:         p[0] = (word)(p-2);
                     66:         p[1] = 0;
                     67:         p[2] = (word)p;
                     68:         p[3] = 0;
                     69:     };
                     70:     return((ptr_t)(p-2));
                     71: }
                     72:
                     73: /* The same for size 3 cleared objects */
                     74: ptr_t GC_build_fl_clear3(h, ofl)
                     75: struct hblk *h;
                     76: ptr_t ofl;
                     77: {
1.3     ! noro       78:     register word * p = h -> hb_body;
1.1       noro       79:     register word * lim = (word *)(h + 1) - 2;
                     80:
                     81:     p[0] = (word)ofl;
                     82:     p[1] = 0;
                     83:     p[2] = 0;
                     84:     p += 3;
                     85:     for (; p < lim; p += 3) {
                     86:         p[0] = (word)(p-3);
                     87:         p[1] = 0;
                     88:         p[2] = 0;
                     89:     };
                     90:     return((ptr_t)(p-3));
                     91: }
                     92:
                     93: /* The same for size 4 cleared objects */
                     94: ptr_t GC_build_fl_clear4(h, ofl)
                     95: struct hblk *h;
                     96: ptr_t ofl;
                     97: {
1.3     ! noro       98:     register word * p = h -> hb_body;
1.1       noro       99:     register word * lim = (word *)(h + 1);
                    100:
                    101:     p[0] = (word)ofl;
                    102:     p[1] = 0;
                    103:     p[2] = 0;
                    104:     p[3] = 0;
                    105:     p += 4;
                    106:     for (; p < lim; p += 4) {
1.2       noro      107:        PREFETCH_FOR_WRITE(p+64);
1.1       noro      108:         p[0] = (word)(p-4);
                    109:         p[1] = 0;
1.2       noro      110:        CLEAR_DOUBLE(p+2);
1.1       noro      111:     };
                    112:     return((ptr_t)(p-4));
                    113: }
                    114:
                    115: /* The same for size 2 uncleared objects */
                    116: ptr_t GC_build_fl2(h, ofl)
                    117: struct hblk *h;
                    118: ptr_t ofl;
                    119: {
1.3     ! noro      120:     register word * p = h -> hb_body;
1.1       noro      121:     register word * lim = (word *)(h + 1);
                    122:
                    123:     p[0] = (word)ofl;
                    124:     p[2] = (word)p;
                    125:     p += 4;
                    126:     for (; p < lim; p += 4) {
                    127:         p[0] = (word)(p-2);
                    128:         p[2] = (word)p;
                    129:     };
                    130:     return((ptr_t)(p-2));
                    131: }
                    132:
                    133: /* The same for size 4 uncleared objects */
                    134: ptr_t GC_build_fl4(h, ofl)
                    135: struct hblk *h;
                    136: ptr_t ofl;
                    137: {
1.3     ! noro      138:     register word * p = h -> hb_body;
1.1       noro      139:     register word * lim = (word *)(h + 1);
                    140:
                    141:     p[0] = (word)ofl;
                    142:     p[4] = (word)p;
                    143:     p += 8;
                    144:     for (; p < lim; p += 8) {
1.2       noro      145:        PREFETCH_FOR_WRITE(p+64);
1.1       noro      146:         p[0] = (word)(p-4);
                    147:         p[4] = (word)p;
                    148:     };
                    149:     return((ptr_t)(p-4));
                    150: }
                    151:
                    152: #endif /* !SMALL_CONFIG */
                    153:
1.3     ! noro      154:
        !           155: /* Build a free list for objects of size sz inside heap block h.       */
        !           156: /* Clear objects inside h if clear is set.  Add list to the end of     */
        !           157: /* the free list we build.  Return the new free list.                  */
        !           158: /* This could be called without the main GC lock, if we ensure that    */
        !           159: /* there is no concurrent collection which might reclaim objects that  */
        !           160: /* we have not yet allocated.                                          */
        !           161: ptr_t GC_build_fl(h, sz, clear, list)
        !           162: struct hblk *h;
        !           163: word sz;
        !           164: GC_bool clear;
        !           165: ptr_t list;
1.1       noro      166: {
1.3     ! noro      167:   word *p, *prev;
        !           168:   word *last_object;           /* points to last object in new hblk    */
1.1       noro      169:
1.3     ! noro      170:   /* Do a few prefetches here, just because its cheap.         */
        !           171:   /* If we were more serious about it, these should go inside  */
        !           172:   /* the loops.  But write prefetches usually don't seem to    */
        !           173:   /* matter much.                                              */
        !           174:     PREFETCH_FOR_WRITE((char *)h);
        !           175:     PREFETCH_FOR_WRITE((char *)h + 128);
        !           176:     PREFETCH_FOR_WRITE((char *)h + 256);
        !           177:     PREFETCH_FOR_WRITE((char *)h + 378);
1.1       noro      178:   /* Handle small objects sizes more efficiently.  For larger objects  */
                    179:   /* the difference is less significant.                               */
                    180: #  ifndef SMALL_CONFIG
                    181:     switch (sz) {
1.3     ! noro      182:         case 1: return GC_build_fl1(h, list);
1.1       noro      183:         case 2: if (clear) {
1.3     ! noro      184:                    return GC_build_fl_clear2(h, list);
1.1       noro      185:                } else {
1.3     ! noro      186:                    return GC_build_fl2(h, list);
1.1       noro      187:                }
                    188:         case 3: if (clear) {
1.3     ! noro      189:                    return GC_build_fl_clear3(h, list);
1.1       noro      190:                } else {
                    191:                    /* It's messy to do better than the default here. */
                    192:                    break;
                    193:                }
                    194:         case 4: if (clear) {
1.3     ! noro      195:                    return GC_build_fl_clear4(h, list);
1.1       noro      196:                } else {
1.3     ! noro      197:                    return GC_build_fl4(h, list);
1.1       noro      198:                }
                    199:         default:
                    200:                break;
                    201:     }
                    202: #  endif /* !SMALL_CONFIG */
                    203:
                    204:   /* Clear the page if necessary. */
                    205:     if (clear) BZERO(h, HBLKSIZE);
                    206:
                    207:   /* Add objects to free list */
                    208:     p = &(h -> hb_body[sz]);   /* second object in *h  */
                    209:     prev = &(h -> hb_body[0]);         /* One object behind p  */
                    210:     last_object = (word *)((char *)h + HBLKSIZE);
                    211:     last_object -= sz;
                    212:                            /* Last place for last object to start */
                    213:
                    214:   /* make a list of all objects in *h with head as last object */
                    215:     while (p <= last_object) {
                    216:       /* current object's link points to last object */
                    217:         obj_link(p) = (ptr_t)prev;
                    218:        prev = p;
                    219:        p += sz;
                    220:     }
                    221:     p -= sz;                   /* p now points to last object */
                    222:
                    223:   /*
                    224:    * put p (which is now head of list of objects in *h) as first
                    225:    * pointer in the appropriate free list for this size.
                    226:    */
1.3     ! noro      227:       obj_link(h -> hb_body) = list;
        !           228:       return ((ptr_t)p);
        !           229: }
        !           230:
        !           231: /*
        !           232:  * Allocate a new heapblock for small objects of size n.
        !           233:  * Add all of the heapblock's objects to the free list for objects
        !           234:  * of that size.
        !           235:  * Set all mark bits if objects are uncollectable.
        !           236:  * Will fail to do anything if we are out of memory.
        !           237:  */
        !           238: void GC_new_hblk(sz, kind)
        !           239: register word sz;
        !           240: int kind;
        !           241: {
        !           242:     register struct hblk *h;   /* the new heap block                   */
        !           243:     register GC_bool clear = GC_obj_kinds[kind].ok_init;
        !           244:
        !           245: #   ifdef PRINTSTATS
        !           246:        if ((sizeof (struct hblk)) > HBLKSIZE) {
        !           247:            ABORT("HBLK SZ inconsistency");
        !           248:         }
        !           249: #   endif
        !           250:
        !           251:   /* Allocate a new heap block */
        !           252:     h = GC_allochblk(sz, kind, 0);
        !           253:     if (h == 0) return;
        !           254:
        !           255:   /* Mark all objects if appropriate. */
        !           256:       if (IS_UNCOLLECTABLE(kind)) GC_set_hdr_marks(HDR(h));
        !           257:
        !           258:   /* Build the free list */
        !           259:       GC_obj_kinds[kind].ok_freelist[sz] =
        !           260:        GC_build_fl(h, sz, clear, GC_obj_kinds[kind].ok_freelist[sz]);
1.1       noro      261: }
                    262:

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>