Line data Source code
1 : /*
2 : * Copyright 1988, 1989 Hans-J. Boehm, Alan J. Demers
3 : * Copyright (c) 1991, 1992 by Xerox Corporation. All rights reserved.
4 : * Copyright (c) 1999-2001 by Hewlett-Packard Company. All rights reserved.
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 :
16 : #include "private/gc_priv.h"
17 :
18 : /* Routines for maintaining maps describing heap block
19 : * layouts for various object sizes. Allows fast pointer validity checks
20 : * and fast location of object start locations on machines (such as SPARC)
21 : * with slow division.
22 : */
23 :
24 : /* Consider pointers that are offset bytes displaced from the beginning */
25 : /* of an object to be valid. */
26 :
27 0 : GC_API void GC_CALL GC_register_displacement(size_t offset)
28 : {
29 : DCL_LOCK_STATE;
30 :
31 0 : LOCK();
32 0 : GC_register_displacement_inner(offset);
33 0 : UNLOCK();
34 0 : }
35 :
36 163 : GC_INNER void GC_register_displacement_inner(size_t offset)
37 : {
38 163 : if (offset >= VALID_OFFSET_SZ) {
39 0 : ABORT("Bad argument to GC_register_displacement");
40 : }
41 163 : if (!GC_valid_offsets[offset]) {
42 163 : GC_valid_offsets[offset] = TRUE;
43 163 : GC_modws_valid_offsets[offset % sizeof(word)] = TRUE;
44 : }
45 163 : }
46 :
47 : #ifdef MARK_BIT_PER_GRANULE
48 : /* Add a heap block map for objects of size granules to obj_map. */
49 : /* Return FALSE on failure. */
50 : /* A size of 0 granules is used for large objects. */
51 53040 : GC_INNER GC_bool GC_add_map_entry(size_t granules)
52 : {
53 : unsigned displ;
54 : short * new_map;
55 :
56 53040 : if (granules > BYTES_TO_GRANULES(MAXOBJBYTES)) granules = 0;
57 53040 : if (GC_obj_map[granules] != 0) {
58 49148 : return(TRUE);
59 : }
60 3892 : new_map = (short *)GC_scratch_alloc(MAP_LEN * sizeof(short));
61 3892 : if (new_map == 0) return(FALSE);
62 3892 : GC_COND_LOG_PRINTF(
63 : "Adding block map for size of %u granules (%u bytes)\n",
64 : (unsigned)granules, (unsigned)GRANULES_TO_BYTES(granules));
65 3892 : if (granules == 0) {
66 36237 : for (displ = 0; displ < BYTES_TO_GRANULES(HBLKSIZE); displ++) {
67 36096 : new_map[displ] = 1; /* Nonzero to get us out of marker fast path. */
68 : }
69 : } else {
70 964007 : for (displ = 0; displ < BYTES_TO_GRANULES(HBLKSIZE); displ++) {
71 960256 : new_map[displ] = (short)(displ % granules);
72 : }
73 : }
74 3892 : GC_obj_map[granules] = new_map;
75 3892 : return(TRUE);
76 : }
77 : #endif /* MARK_BIT_PER_GRANULE */
78 :
79 0 : GC_INNER void GC_initialize_offsets(void)
80 : {
81 : unsigned i;
82 0 : if (GC_all_interior_pointers) {
83 0 : for (i = 0; i < VALID_OFFSET_SZ; ++i)
84 0 : GC_valid_offsets[i] = TRUE;
85 : } else {
86 0 : BZERO(GC_valid_offsets, sizeof(GC_valid_offsets));
87 0 : for (i = 0; i < sizeof(word); ++i)
88 0 : GC_modws_valid_offsets[i] = FALSE;
89 : }
90 0 : }
|