The first step in garbage collection is to mark all heap objects
in use. Each heap cell has a bit reserved for this purpose. For pairs
(cons cells) the lowest order bit (0) of the CDR is used. For other
types, bit 8 of the CAR is used. The GC bits are never set except
during garbage collection. Special C macros are defined in `scm.h'
to allow easy manipulation when GC bits are possibly set. CAR,
TYP3, and TYP7 can be used on GC marked cells as they are.
We need to (recursively) mark only a few objects in order to assure that
all accessible objects are marked. Those objects are
sys_protects[] (for example, dynwinds), the current
C-stack and the hash table for symbols, symhash.
gc_mark() is used for marking SCM cells. If
obj is marked, gc_mark() returns. If obj is
unmarked, gc_mark sets the mark bit in obj, then calls
gc_mark() on any SCM components of obj. The last call to
gc_mark() is tail-called (looped).
mark_locations is used for marking segments of
C-stack or saved segments of C-stack (marked continuations). The
argument len is the size of the stack in units of size
(STACKITEM).
Each longword in the stack is tried to see if it is a valid cell pointer
into the heap. If it is, the object itself and any objects it points to
are marked using gc_mark. If the stack is word rather than
longword aligned (#define WORD_ALIGN), both alignments are tried.
This arrangement will occasionally mark an object which is no longer
used. This has not been a problem in practice and the advantage of
using the c-stack far outweighs it.