123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384 |
- @node Interacting with the Scheme heap in C
- @section Interacting with the Scheme heap in C
- @cindex GC protection in C
- Scheme48 uses a precise copying garbage collector. Any code that
- allocates objects within the Scheme48 heap may trigger a garbage
- collection. Variables bound to values in the Scheme48 heap need to be
- registered with the garbage collector so that the value will be safely
- held and so that the variables will be updated if the garbage collector
- moves the object. The garbage collector has no facility for updating
- pointers to the interiors of objects, so such pointers, for example the
- ones returned by @code{S48_EXTRACT_STRING}, will likely become invalid
- when a garbage collection occurs.
- @deftypefn {C macro} {} S48_DECLARE_GC_PROTECT (@var{n})
- @deftypefnx {C macro} void S48_GC_PROTECT_@var{n} (s48_value @var{var}@sub{1}, @dots{}, s48_value @var{var}@sub{@var{n}})
- @deftypefnx {C macro} void S48_GC_UNPROTECT ()
- @code{S48_DECLARE_GC_PROTECT}, where 1 <= @var{n} <= 9, allocates
- storage for registering @var{n} variables. At most one use of
- @code{S48_DECLARE_GC_PROTECT} may occur in a block. After declaring a
- GC protection, @code{S48_GC_PROTECT_@var{n}} registers the @var{n}
- variables with the garbage collector. It must be within the scope that
- the @code{S48_DECLARE_GC_PROTECT} occurred in and before any code that
- can cause a garbage collection. @code{S48_GC_UNPROTECT} removes the
- current block's protected variables from the garbage collector's list.
- It must be called at the end of the block after any code that may cause
- a garbage collection. Omitting any of the three may cause serious and
- hard-to-debug problems, because the garbage collector may relocate an
- object and invalidate unprotected @code{s48_value} pointers. If not
- @code{S48_DECLARE_GC_PROTECT} is matched with a @code{S48_GC_UNPROTECT}
- or vice versa, a @code{gc-protection-mismatch} exception is raised when
- a C procedure returns to Scheme.
- @end deftypefn
- @deftypefn {C macro} {void *} S48_GC_PROTECT_GLOBAL (@var{global})
- @deftypefnx {C macro} void S48_GC_UNPROTECT_GLOBAL (void *@var{handle})
- @code{S48_GC_PROTECT_GLOBAL} permanently registers the l-value
- @var{global} with the system as a garbage collection root. It returns
- a pointer which may then be supplied to @code{S48_GC_UNPROTECT_GLOBAL}
- to unregister the l-value as a root.
- @end deftypefn
- @subsection Keeping C data structures in the Scheme heap
- @cindex storing C data in the Scheme heap
- C data structures can be stored within the Scheme heap by embedding
- them inside @embedref{Bitwise manipulation, byte vectors}. The
- following macros can be used to create and access embedded C objects.
- @deftypefn {C macro} s48_value S48_MAKE_VALUE (@var{type})
- @deftypefnx {C macro} @var{type} S48_EXTRACT_VALUE (s48_value @var{bytev}, @var{type})
- @deftypefnx {C macro} {@var{type} *} S48_EXTRACT_VALUE_POINTER (s48_value @var{bytev}, @var{type})
- @deftypefnx {C macro} void S48_SET_VALUE (s48_value @var{bytev}, @var{type}, @var{type} @var{value})
- @code{S48_MAKE_VALUE} allocates a byte vector large enough to hold a C
- value whose type is @var{type}. @code{S48_EXTRACT_VALUE} returns the
- contents of the byte vector @var{bytev} cast to @var{type}, and
- @code{S48_EXTRACT_VALUE_POINTER} returns a pointer to the contents of
- the byte vector, which is valid only until the next garbage collection.
- @code{S48_SET_VALUE} stores a value into the byte vector.
- @end deftypefn
- @subsection C code and heap images
- @cindex restoring C data after resuming images
- @cindex dumping Scheme heap images with C data
- @cindex record resumers
- Scheme48 uses dumped heap images to restore a previous system state.
- The Scheme48 heap is written into a file in a machine-independent and
- operating-system-independent format. The procedures described above,
- however, may be used to create objects in the Scheme heap that contain
- information specific to the current machine, operating system, or
- process. A heap image containing such objects may not work correctly
- when resumed.
- To address this problem, a record type may be given a @dfn{resumer}
- procedure. On startup, the resumer procedure for a record type is
- applied to each record of that type in the image being restarted. This
- procedure can update the record in a manner appropriate to the machine,
- operating system, or process used to resume the image. Note, though,
- that there is no reliable order in which record resumer procedures are
- applied. To specify the resumer for a record type, use the
- @code{define-record-resumer} procedure from the @embedref{Records,
- @code{record-types} structure}.
|