diff --git a/libguile/bytevectors.c b/libguile/bytevectors.c index 9093f49c3..db24f91b1 100644 --- a/libguile/bytevectors.c +++ b/libguile/bytevectors.c @@ -332,10 +332,11 @@ scm_c_shrink_bytevector (SCM bv, size_t c_new_len) SCM_BYTEVECTOR_SET_LENGTH (bv, c_new_len); if (SCM_BYTEVECTOR_CONTIGUOUS_P (bv)) - new_bv = PTR2SCM (scm_gc_realloc (SCM2PTR (bv), - c_len + SCM_BYTEVECTOR_HEADER_BYTES, - c_new_len + SCM_BYTEVECTOR_HEADER_BYTES, - SCM_GC_BYTEVECTOR)); + new_bv = SCM_PACK_POINTER + (scm_gc_realloc (SCM_HEAP_OBJECT_BASE (bv), + c_len + SCM_BYTEVECTOR_HEADER_BYTES, + c_new_len + SCM_BYTEVECTOR_HEADER_BYTES, + SCM_GC_BYTEVECTOR)); else { signed char *c_bv; diff --git a/libguile/fluids.c b/libguile/fluids.c index 8e36acde6..4844b7a0c 100644 --- a/libguile/fluids.c +++ b/libguile/fluids.c @@ -151,7 +151,7 @@ new_fluid (SCM init) SCM_SET_CELL_WORD_0 (fluid, (scm_tc7_fluid | (n << 8))); GC_GENERAL_REGISTER_DISAPPEARING_LINK (&allocated_fluids[n], - SCM2PTR (fluid)); + SCM_HEAP_OBJECT_BASE (fluid)); scm_dynwind_end (); diff --git a/libguile/foreign.c b/libguile/foreign.c index 47077f7f8..a8e1da052 100644 --- a/libguile/foreign.c +++ b/libguile/foreign.c @@ -1,4 +1,4 @@ -/* Copyright (C) 2010, 2011, 2012 Free Software Foundation, Inc. +/* Copyright (C) 2010, 2011, 2012, 2013 Free Software Foundation, Inc. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public License @@ -157,7 +157,8 @@ scm_from_pointer (void *ptr, scm_t_pointer_finalizer finalizer) ret = scm_cell (scm_tc7_pointer, (scm_t_bits) ptr); if (finalizer) - scm_i_set_finalizer (SCM2PTR (ret), pointer_finalizer_trampoline, + scm_i_set_finalizer (SCM_HEAP_OBJECT_BASE (ret), + pointer_finalizer_trampoline, finalizer); } @@ -311,7 +312,7 @@ SCM_DEFINE (scm_set_pointer_finalizer_x, "set-pointer-finalizer!", 2, 0, 0, SCM_VALIDATE_POINTER (1, pointer); SCM_VALIDATE_POINTER (2, finalizer); - scm_i_add_finalizer (SCM2PTR (pointer), pointer_finalizer_trampoline, + scm_i_add_finalizer (SCM_HEAP_OBJECT_BASE (pointer), pointer_finalizer_trampoline, SCM_POINTER_VALUE (finalizer)); return SCM_UNSPECIFIED; diff --git a/libguile/gc.h b/libguile/gc.h index b1df82df5..d81546d74 100644 --- a/libguile/gc.h +++ b/libguile/gc.h @@ -46,12 +46,13 @@ typedef struct scm_t_cell * in debug mode. In particular these macros will even work for free cells, * which should never be encountered by user code. */ -#define SCM_GC_CELL_OBJECT(x, n) (((SCM *)SCM2PTR (x)) [n]) -#define SCM_GC_CELL_WORD(x, n) (SCM_UNPACK (SCM_GC_CELL_OBJECT ((x), (n)))) +#define SCM_GC_CELL_OBJECT(x, n) (SCM_PACK (SCM_HEAP_OBJECT_BASE (x)[n])) +#define SCM_GC_CELL_WORD(x, n) (SCM_HEAP_OBJECT_BASE (x)[n]) -#define SCM_GC_SET_CELL_OBJECT(x, n, v) ((((SCM *)SCM2PTR (x)) [n]) = (v)) +#define SCM_GC_SET_CELL_OBJECT(x, n, v) \ + (SCM_HEAP_OBJECT_BASE (x)[n] = SCM_UNPACK (v)) #define SCM_GC_SET_CELL_WORD(x, n, v) \ - (SCM_GC_SET_CELL_OBJECT ((x), (n), SCM_PACK (v))) + (SCM_HEAP_OBJECT_BASE (x)[n] = (v)) #define SCM_GC_CELL_TYPE(x) (SCM_GC_CELL_OBJECT ((x), 0)) @@ -97,7 +98,8 @@ typedef struct scm_t_cell #define SCM_SET_CELL_OBJECT_2(x, v) SCM_SET_CELL_OBJECT ((x), 2, (v)) #define SCM_SET_CELL_OBJECT_3(x, v) SCM_SET_CELL_OBJECT ((x), 3, (v)) -#define SCM_CELL_OBJECT_LOC(x, n) (SCM_VALIDATE_CELL((x), &SCM_GC_CELL_OBJECT ((x), (n)))) +#define SCM_CELL_WORD_LOC(x, n) (SCM_VALIDATE_CELL((x), &SCM_GC_CELL_WORD ((x), (n)))) +#define SCM_CELL_OBJECT_LOC(x, n) ((SCM *) SCM_CELL_WORD_LOC (x, n)) #define SCM_CARLOC(x) (SCM_CELL_OBJECT_LOC ((x), 0)) #define SCM_CDRLOC(x) (SCM_CELL_OBJECT_LOC ((x), 1)) diff --git a/libguile/guardians.c b/libguile/guardians.c index 8a0d2961c..4944a32ef 100644 --- a/libguile/guardians.c +++ b/libguile/guardians.c @@ -219,6 +219,8 @@ scm_i_guard (SCM guardian, SCM obj) SCM_EOL); finalizer_data = scm_cons (SCM_BOOL_F, guardians_for_obj); + /* FIXME: should be SCM_HEAP_OBJECT_BASE, but will the finalizer + strip the tag bits of pairs or structs? */ GC_REGISTER_FINALIZER_NO_ORDER (SCM_UNPACK_POINTER (obj), finalize_guarded, SCM_UNPACK_POINTER (finalizer_data), &prev_finalizer, &prev_data); diff --git a/libguile/macros.c b/libguile/macros.c index 47b252d85..c9745cdbd 100644 --- a/libguile/macros.c +++ b/libguile/macros.c @@ -103,7 +103,7 @@ SCM_DEFINE (scm_make_syntax_transformer, "make-syntax-transformer", 3, 0, 0, SCM_VALIDATE_SYMBOL (2, type); z = scm_words (scm_tc16_macro, 5); - SCM_SET_SMOB_DATA_N (z, 1, prim); + SCM_SET_SMOB_DATA_N (z, 1, (scm_t_bits)prim); SCM_SET_SMOB_OBJECT_N (z, 2, name); SCM_SET_SMOB_OBJECT_N (z, 3, type); SCM_SET_SMOB_OBJECT_N (z, 4, binding); diff --git a/libguile/numbers.h b/libguile/numbers.h index cef2b863b..b7bcfe48c 100644 --- a/libguile/numbers.h +++ b/libguile/numbers.h @@ -128,9 +128,9 @@ typedef scm_t_int32 scm_t_wchar; #define SCM_REALP(x) (SCM_HAS_TYP16 (x, scm_tc16_real)) #define SCM_COMPLEXP(x) (SCM_HAS_TYP16 (x, scm_tc16_complex)) -#define SCM_REAL_VALUE(x) (((scm_t_double *) SCM2PTR (x))->real) -#define SCM_COMPLEX_REAL(x) (((scm_t_complex *) SCM2PTR (x))->real) -#define SCM_COMPLEX_IMAG(x) (((scm_t_complex *) SCM2PTR (x))->imag) +#define SCM_REAL_VALUE(x) (((scm_t_double *) SCM_HEAP_OBJECT_BASE (x))->real) +#define SCM_COMPLEX_REAL(x) (((scm_t_complex *) SCM_HEAP_OBJECT_BASE (x))->real) +#define SCM_COMPLEX_IMAG(x) (((scm_t_complex *) SCM_HEAP_OBJECT_BASE (x))->imag) /* Each bignum is just an mpz_t stored in a double cell starting at word 1. */ #define SCM_I_BIG_MPZ(x) (*((mpz_t *) (SCM_CELL_OBJECT_LOC((x),1)))) diff --git a/libguile/ports.c b/libguile/ports.c index 0aacacc06..02f4ea1d9 100644 --- a/libguile/ports.c +++ b/libguile/ports.c @@ -676,7 +676,7 @@ scm_c_make_port_with_encoding (scm_t_bits tag, unsigned long mode_bits, entry->alist = SCM_EOL; if (SCM_PORT_DESCRIPTOR (ret)->free) - scm_i_set_finalizer (SCM2PTR (ret), finalize_port, NULL); + scm_i_set_finalizer (SCM_HEAP_OBJECT_BASE (ret), finalize_port, NULL); if (SCM_PORT_DESCRIPTOR (ret)->flags & SCM_PORT_TYPE_HAS_FLUSH) scm_weak_set_add_x (scm_i_port_weak_set, ret); diff --git a/libguile/smob.c b/libguile/smob.c index c2347f3be..6dc2dfd83 100644 --- a/libguile/smob.c +++ b/libguile/smob.c @@ -1,4 +1,4 @@ -/* Copyright (C) 1995,1996,1998,1999,2000,2001, 2003, 2004, 2006, 2009, 2010, 2011, 2012 Free Software Foundation, Inc. +/* Copyright (C) 1995,1996,1998,1999,2000,2001, 2003, 2004, 2006, 2009, 2010, 2011, 2012, 2013 Free Software Foundation, Inc. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public License @@ -414,7 +414,7 @@ scm_i_new_smob (scm_t_bits tc, scm_t_bits data) SCM_SET_CELL_WORD_0 (ret, tc); if (scm_smobs[smobnum].free) - scm_i_set_finalizer (SCM2PTR (ret), finalize_smob, NULL); + scm_i_set_finalizer (SCM_HEAP_OBJECT_BASE (ret), finalize_smob, NULL); return ret; } @@ -441,7 +441,7 @@ scm_i_new_double_smob (scm_t_bits tc, scm_t_bits data1, SCM_SET_CELL_WORD_0 (ret, tc); if (scm_smobs[smobnum].free) - scm_i_set_finalizer (SCM2PTR (ret), finalize_smob, NULL); + scm_i_set_finalizer (SCM_HEAP_OBJECT_BASE (ret), finalize_smob, NULL); return ret; } diff --git a/libguile/struct.c b/libguile/struct.c index 1a30fefc5..ed75b8ba5 100644 --- a/libguile/struct.c +++ b/libguile/struct.c @@ -1,4 +1,4 @@ -/* Copyright (C) 1996,1997,1998,1999,2000,2001, 2003, 2004, 2006, 2007, 2008, 2009, 2010, 2011, 2012 Free Software Foundation, Inc. +/* Copyright (C) 1996,1997,1998,1999,2000,2001, 2003, 2004, 2006, 2007, 2008, 2009, 2010, 2011, 2012, 2013 Free Software Foundation, Inc. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public License @@ -445,7 +445,8 @@ scm_i_alloc_struct (scm_t_bits *vtable_data, int n_words) /* vtable_data can be null when making a vtable vtable */ if (vtable_data && vtable_data[scm_vtable_index_instance_finalize]) /* Register a finalizer for the newly created instance. */ - scm_i_set_finalizer (SCM2PTR (ret), struct_finalizer_trampoline, NULL); + scm_i_set_finalizer (SCM_HEAP_OBJECT_BASE (ret), + struct_finalizer_trampoline, NULL); return ret; } diff --git a/libguile/tags.h b/libguile/tags.h index a194ea0be..043bdbdce 100644 --- a/libguile/tags.h +++ b/libguile/tags.h @@ -391,6 +391,17 @@ typedef union SCM { struct { scm_t_bits n; } n; } SCM; #define scm_tc3_tc7_2 7 +/* As we have seen, heap objects have a tag in their three lowest bits. + If you have a heap object and want the pointer to the start of the + object, perhaps for GC purposes, you need to mask off the low bits, + which is what SCM_HEAP_OBJECT_BASE does. + + Note that you can avoid this macro if you know the specific type of + the object (pair, struct, or other). + */ +#define SCM_HEAP_OBJECT_BASE(x) ((scm_t_bits*)((SCM_UNPACK (x)) & ~7)) + + /* Definitions for tc7: */ #define SCM_ITAG7(x) (127 & SCM_UNPACK (x)) diff --git a/libguile/weak-set.c b/libguile/weak-set.c index d648dbd34..e127cc83f 100644 --- a/libguile/weak-set.c +++ b/libguile/weak-set.c @@ -1,4 +1,4 @@ -/* Copyright (C) 2011, 2012 Free Software Foundation, Inc. +/* Copyright (C) 2011, 2012, 2013 Free Software Foundation, Inc. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public License @@ -580,7 +580,7 @@ weak_set_add_x (scm_t_weak_set *set, unsigned long hash, if (SCM_HEAP_OBJECT_P (obj)) SCM_I_REGISTER_DISAPPEARING_LINK ((void **) &entries[k].key, - (void *) SCM2PTR (obj)); + (void *) SCM_HEAP_OBJECT_BASE (obj)); return obj; } @@ -743,7 +743,7 @@ scm_c_register_weak_gc_callback (SCM obj, void (*callback) (SCM)) weak[0] = SCM_UNPACK_POINTER (obj); weak[1] = (void*)callback; - GC_GENERAL_REGISTER_DISAPPEARING_LINK (weak, SCM2PTR (obj)); + GC_GENERAL_REGISTER_DISAPPEARING_LINK (weak, SCM_HEAP_OBJECT_BASE (obj)); #ifdef HAVE_GC_SET_START_CALLBACK scm_c_hook_add (&scm_after_gc_c_hook, weak_gc_hook, weak, 0); diff --git a/libguile/weak-table.c b/libguile/weak-table.c index 9ef6674e1..85d587a45 100644 --- a/libguile/weak-table.c +++ b/libguile/weak-table.c @@ -1,4 +1,4 @@ -/* Copyright (C) 2011, 2012 Free Software Foundation, Inc. +/* Copyright (C) 2011, 2012, 2013 Free Software Foundation, Inc. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public License @@ -131,13 +131,13 @@ register_disappearing_links (scm_t_weak_entry *entry, && (kind == SCM_WEAK_TABLE_KIND_KEY || kind == SCM_WEAK_TABLE_KIND_BOTH)) SCM_I_REGISTER_DISAPPEARING_LINK ((void **) &entry->key, - SCM2PTR (k)); + SCM_HEAP_OBJECT_BASE (k)); if (SCM_UNPACK (v) && SCM_HEAP_OBJECT_P (v) && (kind == SCM_WEAK_TABLE_KIND_VALUE || kind == SCM_WEAK_TABLE_KIND_BOTH)) SCM_I_REGISTER_DISAPPEARING_LINK ((void **) &entry->value, - SCM2PTR (v)); + SCM_HEAP_OBJECT_BASE (v)); } static void @@ -162,7 +162,7 @@ move_disappearing_links (scm_t_weak_entry *from, scm_t_weak_entry *to, GC_move_disappearing_link ((void **) &from->key, (void **) &to->key); #else GC_unregister_disappearing_link ((void **) &from->key); - SCM_I_REGISTER_DISAPPEARING_LINK ((void **) &to->key, SCM2PTR (key)); + SCM_I_REGISTER_DISAPPEARING_LINK ((void **) &to->key, SCM_HEAP_OBJECT_BASE (key)); #endif } @@ -173,7 +173,7 @@ move_disappearing_links (scm_t_weak_entry *from, scm_t_weak_entry *to, GC_move_disappearing_link ((void **) &from->value, (void **) &to->value); #else GC_unregister_disappearing_link ((void **) &from->value); - SCM_I_REGISTER_DISAPPEARING_LINK ((void **) &to->value, SCM2PTR (value)); + SCM_I_REGISTER_DISAPPEARING_LINK ((void **) &to->value, SCM_HEAP_OBJECT_BASE (value)); #endif } } @@ -328,7 +328,7 @@ mark_weak_key_table (GC_word *addr, struct GC_ms_entry *mark_stack_ptr, if (entries[k].hash && entries[k].key) { SCM value = SCM_PACK (entries[k].value); - mark_stack_ptr = GC_MARK_AND_PUSH ((GC_word*) SCM2PTR (value), + mark_stack_ptr = GC_MARK_AND_PUSH ((GC_word*) SCM_HEAP_OBJECT_BASE (value), mark_stack_ptr, mark_stack_limit, NULL); } @@ -347,7 +347,7 @@ mark_weak_value_table (GC_word *addr, struct GC_ms_entry *mark_stack_ptr, if (entries[k].hash && entries[k].value) { SCM key = SCM_PACK (entries[k].key); - mark_stack_ptr = GC_MARK_AND_PUSH ((GC_word*) SCM2PTR (key), + mark_stack_ptr = GC_MARK_AND_PUSH ((GC_word*) SCM_HEAP_OBJECT_BASE (key), mark_stack_ptr, mark_stack_limit, NULL); } @@ -864,7 +864,7 @@ scm_c_register_weak_gc_callback (SCM obj, void (*callback) (SCM)) weak[0] = SCM_UNPACK_POINTER (obj); weak[1] = (void*)callback; - GC_GENERAL_REGISTER_DISAPPEARING_LINK (weak, SCM2PTR (obj)); + GC_GENERAL_REGISTER_DISAPPEARING_LINK (weak, SCM_HEAP_OBJECT_BASE (obj)); #ifdef HAVE_GC_TABLE_START_CALLBACK scm_c_hook_add (&scm_after_gc_c_hook, weak_gc_hook, weak, 0); diff --git a/libguile/weak-vector.c b/libguile/weak-vector.c index 3e90b3d57..17c574a07 100644 --- a/libguile/weak-vector.c +++ b/libguile/weak-vector.c @@ -1,4 +1,4 @@ -/* Copyright (C) 1995,1996,1998,2000,2001, 2003, 2006, 2008, 2009, 2010, 2011, 2012 Free Software Foundation, Inc. +/* Copyright (C) 1995,1996,1998,2000,2001, 2003, 2006, 2008, 2009, 2010, 2011, 2012, 2013 Free Software Foundation, Inc. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public License @@ -177,7 +177,7 @@ scm_c_weak_vector_set_x (SCM wv, size_t k, SCM x) if (SCM_HEAP_OBJECT_P (x)) SCM_I_REGISTER_DISAPPEARING_LINK ((void **) &elts[k], - SCM2PTR (x)); + SCM_HEAP_OBJECT_BASE (x)); }