diff options
author | Paul Eggert <eggert@cs.ucla.edu> | 2014-09-30 12:10:37 -0700 |
---|---|---|
committer | Paul Eggert <eggert@cs.ucla.edu> | 2014-09-30 12:10:37 -0700 |
commit | 4dfc68b1db75006f7b5642fea6875e74197400d4 (patch) | |
tree | 20619d5f452dbaa8df5e2fea20a995cfdb238e99 | |
parent | b2e14af82cf006084acd9177ca8e47fc61ba6779 (diff) | |
download | emacs-4dfc68b1db75006f7b5642fea6875e74197400d4.tar.gz |
* internals.texi (Stack-allocated Objects): Further improvements.
Give an example of misuse.
-rw-r--r-- | doc/lispref/ChangeLog | 5 | ||||
-rw-r--r-- | doc/lispref/internals.texi | 63 |
2 files changed, 49 insertions, 19 deletions
diff --git a/doc/lispref/ChangeLog b/doc/lispref/ChangeLog index 0aba61e53e9..576a772d730 100644 --- a/doc/lispref/ChangeLog +++ b/doc/lispref/ChangeLog @@ -1,3 +1,8 @@ +2014-09-30 Paul Eggert <eggert@cs.ucla.edu> + + * internals.texi (Stack-allocated Objects): Further improvements. + Give an example of misuse. + 2014-09-30 Eli Zaretskii <eliz@gnu.org> * internals.texi (Stack-allocated Objects): Minor improvements of diff --git a/doc/lispref/internals.texi b/doc/lispref/internals.texi index 3ef82eb81aa..6c7ff038149 100644 --- a/doc/lispref/internals.texi +++ b/doc/lispref/internals.texi @@ -537,25 +537,50 @@ floating-point number. @cindex Lisp objects, stack-allocated The garbage collector described above is used to manage data visible from Lisp programs, as well as most of the data internally used by the -Lisp interpreter. But sometimes it may be useful to allocate -temporary internal (i.e.@: not visible for a Lisp program) objects -using the C stack of the interpreter. Currently, only cons cells and -strings can be allocated that way. Stack-allocated strings are -limited to @acronym{ASCII} characters only, and should be treated as -immutable (calling @code{ASET} on them produces undefined behavior). - - In C, this is implemented as special macros which expand into a -@code{Lisp_Object} with block-scoped semantics and lifetime (see the -code around @code{USE_STACK_LISP_OBJECTS} in @file{src/lisp.h}). This -means that these objects are not freed by the garbage collector; -instead, they are allocated like local variables in C and -automatically freed when execution goes out of the scope where the -object was allocated. Thus, allocating and freeing these objects is -faster than when using heap memory to allocate and the garbage -collector to free their memory. Note that using such objects out of -their scope will result in undefined behavior, so code using them -should be well thought out and carefully debugged by using the -@code{GC_CHECK_MARKED_OBJECTS} feature (see @file{src/alloc.c}). +Lisp interpreter. Sometimes it may be useful to allocate temporary +internal objects using the C stack of the interpreter. This can help +performance, as stack allocation is typically faster than using heap +memory to allocate and the garbage collector to free. The downside is +that using such objects after they are freed results in undefined +behavior, so uses should be well thought out and carefully debugged by +using the @code{GC_CHECK_MARKED_OBJECTS} feature (see +@file{src/alloc.c}). In particular, stack-allocated objects should +never be made visible to user Lisp code. + + Currently, cons cells and strings can be allocated this way. This +is implemented by C macros like @code{scoped_cons} and +@code{SCOPED_STRING} that return a @code{Lisp_Object} with block +lifetime. These objects are not freed by the garbage collector; +instead, they have automatic storage duration, i.e., they are +allocated like local variables and are automatically freed at the end +of execution of the C block where the object was allocated. C blocks +include compound statements (i.e., inside @samp{@{} and @samp{@}}), +along with selection and iteration statements and their immediate +substatements. For example: + +@example +/* Erroneous code. */ +Lisp_Object x; +if (foo) + x = SCOPED_STRING ("prefix"); +else + x = bar; +return concat2 (x, baz); +@end example + +@noindent +This has undefined behavior because the @code{if} statement is a +block, so @code{x} is used after the corresponding object has been +freed. Better would be: + +@example +Lisp_Object x = foo ? SCOPED_STRING ("prefix") : bar; +return concat2 (x, baz); +@end example + + For performance reasons, stack-allocated strings are limited to +@acronym{ASCII} characters, and many of these strings are immutable, +i.e., calling @code{ASET} on them produces undefined behavior. @node Memory Usage @section Memory Usage |