1
Fork 0
mirror of https://git.savannah.gnu.org/git/guile.git synced 2025-05-20 11:40:18 +02:00

Clarify use of the term "scanning" in the manual

* doc/ref/api-memory.texi (Garbage Collection Functions):
* doc/ref/libguile-concepts.texi (Garbage Collection): Attempt to be
  clear that scanning is a thing that happens in the mark phase.  Fixes
  #20907 I think.
This commit is contained in:
Andy Wingo 2016-06-24 08:56:21 +02:00
parent f23dfc0fb5
commit f84006c564
2 changed files with 56 additions and 34 deletions

View file

@ -27,9 +27,10 @@ collection relates to using Guile from C.
@deffn {Scheme Procedure} gc @deffn {Scheme Procedure} gc
@deffnx {C Function} scm_gc () @deffnx {C Function} scm_gc ()
Scans all of SCM objects and reclaims for further use those that are Finds all of the ``live'' @code{SCM} objects and reclaims for further
no longer accessible. You normally don't need to call this function use those that are no longer accessible. You normally don't need to
explicitly. It is called automatically when appropriate. call this function explicitly. Its functionality is invoked
automatically as needed.
@end deffn @end deffn
@deftypefn {C Function} SCM scm_gc_protect_object (SCM @var{obj}) @deftypefn {C Function} SCM scm_gc_protect_object (SCM @var{obj})
@ -43,8 +44,9 @@ than it has been protected. Returns the SCM object it was passed.
Note that storing @var{obj} in a C global variable has the same Note that storing @var{obj} in a C global variable has the same
effect@footnote{In Guile up to version 1.8, C global variables were not effect@footnote{In Guile up to version 1.8, C global variables were not
scanned by the garbage collector; hence, @code{scm_gc_protect_object} visited by the garbage collector in the mark phase; hence,
was the only way in C to prevent a Scheme object from being freed.}. @code{scm_gc_protect_object} was the only way in C to prevent a Scheme
object from being freed.}.
@end deftypefn @end deftypefn
@deftypefn {C Function} SCM scm_gc_unprotect_object (SCM @var{obj}) @deftypefn {C Function} SCM scm_gc_unprotect_object (SCM @var{obj})
@ -123,16 +125,18 @@ live reference to it@footnote{In Guile up to version 1.8, memory
allocated with @code{scm_gc_malloc} @emph{had} to be freed with allocated with @code{scm_gc_malloc} @emph{had} to be freed with
@code{scm_gc_free}.}. @code{scm_gc_free}.}.
Memory allocated with @code{scm_gc_malloc} is scanned for live pointers. When garbage collection occurs, Guile will visit the words in memory
This means that if @code{scm_gc_malloc}-allocated memory contains a allocated with @code{scm_gc_malloc}, looking for live pointers. This
pointer to some other part of the memory, the garbage collector notices means that if @code{scm_gc_malloc}-allocated memory contains a pointer
it and prevents it from being reclaimed@footnote{In Guile up to 1.8, to some other part of the memory, the garbage collector notices it and
memory allocated with @code{scm_gc_malloc} was @emph{not} scanned. prevents it from being reclaimed@footnote{In Guile up to 1.8, memory
Consequently, the GC had to be told explicitly about pointers to live allocated with @code{scm_gc_malloc} was @emph{not} visited by the
objects contained in the memory block, e.g., @i{via} SMOB mark functions collector in the mark phase. Consequently, the GC had to be told
(@pxref{Smobs, @code{scm_set_smob_mark}})}. Conversely, memory explicitly about pointers to live objects contained in the memory block,
allocated with @code{scm_gc_malloc_pointerless} is assumed to be e.g., @i{via} SMOB mark functions (@pxref{Smobs,
``pointer-less'' and is not scanned. @code{scm_set_smob_mark}})}. Conversely, memory allocated with
@code{scm_gc_malloc_pointerless} is assumed to be ``pointer-less'' and
is not scanned for pointers.
For memory that is not associated with a Scheme object, you can use For memory that is not associated with a Scheme object, you can use
@code{scm_malloc} instead of @code{malloc}. Like @code{scm_malloc} instead of @code{malloc}. Like
@ -193,9 +197,11 @@ Allocate @var{size} bytes of automatically-managed memory. The memory
is automatically freed when no longer referenced from any live memory is automatically freed when no longer referenced from any live memory
block. block.
Memory allocated with @code{scm_gc_malloc} or @code{scm_gc_calloc} is When garbage collection occurs, Guile will visit the words in memory
scanned for pointers. Memory allocated by allocated with @code{scm_gc_malloc} or @code{scm_gc_calloc}, looking for
@code{scm_gc_malloc_pointerless} is not scanned. pointers to other memory allocations that are managed by the GC. In
contrast, memory allocated by @code{scm_gc_malloc_pointerless} is not
scanned for pointers.
The @code{scm_gc_realloc} call preserves the ``pointerlessness'' of the The @code{scm_gc_realloc} call preserves the ``pointerlessness'' of the
memory area pointed to by @var{mem}. Note that you need to pass the old memory area pointed to by @var{mem}. Note that you need to pass the old

View file

@ -203,22 +203,38 @@ set'' of garbage collection; any value on the heap that is referenced
directly or indirectly by a member of the root set is preserved, and all directly or indirectly by a member of the root set is preserved, and all
other objects are eligible for reclamation. other objects are eligible for reclamation.
The Scheme stack and heap are scanned precisely; that is to say, Guile In Guile, garbage collection has two logical phases: the @dfn{mark
knows about all inter-object pointers on the Scheme stack and heap. phase}, in which the collector discovers the set of all live objects,
This is not the case, unfortunately, for pointers on the C stack and and the @dfn{sweep phase}, in which the collector reclaims the resources
static data segment. For this reason we have to scan the C stack and associated with dead objects. The mark phase pauses the program and
static data segment @dfn{conservatively}; any value that looks like a traces all @code{SCM} object references, starting with the root set.
pointer to a GC-managed object is treated as such, whether it actually The sweep phase actually runs concurrently with the main program,
is a reference or not. Thus, scanning the C stack and static data incrementally reclaiming memory as needed by allocation.
segment is guaranteed to find all actual references, but it might also
find words that only accidentally look like references. These ``false In the mark phase, the garbage collector traces the Scheme stack and
positives'' might keep @code{SCM} objects alive that would otherwise be heap @dfn{precisely}. Because the Scheme stack and heap are managed by
considered dead. While this might waste memory, keeping an object Guile, Guile can know precisely where in those data structures it might
around longer than it strictly needs to is harmless. This is why this find references to other heap objects. This is not the case,
technique is called ``conservative garbage collection''. In practice, unfortunately, for pointers on the C stack and static data segment.
the wasted memory seems to be no problem, as the static C root set is Instead of requiring the user to inform Guile about all variables in C
almost always finite and small, given that the Scheme stack is separate that might point to heap objects, Guile traces the C stack and static
from the C stack. data segment @dfn{conservatively}. That is to say, Guile just treats
every word on the C stack and every C global variable as a potential
reference in to the Scheme heap@footnote{Note that Guile does not scan
the C heap for references, so a reference to a @code{SCM} object from a
memory segment allocated with @code{malloc} will have to use some other
means to keep the @code{SCM} object alive. @xref{Garbage Collection
Functions}.}. Any value that looks like a pointer to a GC-managed
object is treated as such, whether it actually is a reference or not.
Thus, scanning the C stack and static data segment is guaranteed to find
all actual references, but it might also find words that only
accidentally look like references. These ``false positives'' might keep
@code{SCM} objects alive that would otherwise be considered dead. While
this might waste memory, keeping an object around longer than it
strictly needs to is harmless. This is why this technique is called
``conservative garbage collection''. In practice, the wasted memory
seems to be no problem, as the static C root set is almost always finite
and small, given that the Scheme stack is separate from the C stack.
The stack of every thread is scanned in this way and the registers of The stack of every thread is scanned in this way and the registers of
the CPU and all other memory locations where local variables or function the CPU and all other memory locations where local variables or function