mirror of
https://git.savannah.gnu.org/git/guile.git
synced 2025-06-04 11:10:27 +02:00
Renamed the "frames" that are related to dynamic-wind to "dynamic
contexts. Renamed all functions from scm_frame_ to scm_dynwind_. Updated documentation.
This commit is contained in:
parent
15ccf10bf2
commit
661ae7ab6b
43 changed files with 462 additions and 449 deletions
37
NEWS
37
NEWS
|
@ -1012,50 +1012,51 @@ prevent a potential memory leak:
|
|||
{
|
||||
char *mem;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
mem = scm_malloc (100);
|
||||
scm_frame_unwind_handler (free, mem, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_unwind_handler (free, mem, SCM_F_WIND_EXPLICITLY);
|
||||
|
||||
/* MEM would leak if BAR throws an error.
|
||||
SCM_FRAME_UNWIND_HANDLER frees it nevertheless.
|
||||
SCM_DYNWIND_UNWIND_HANDLER frees it nevertheless.
|
||||
*/
|
||||
|
||||
bar ();
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
|
||||
/* Because of SCM_F_WIND_EXPLICITLY, MEM will be freed by
|
||||
SCM_FRAME_END as well.
|
||||
SCM_DYNWIND_END as well.
|
||||
*/
|
||||
}
|
||||
|
||||
For full documentation, see the node "Frames" in the manual.
|
||||
For full documentation, see the node "Dynamic Wind" in the manual.
|
||||
|
||||
** New function scm_frame_free
|
||||
** New function scm_dynwind_free
|
||||
|
||||
This function calls 'free' on a given pointer when a frame is left.
|
||||
Thus the call to scm_frame_unwind_handler above could be replaced with
|
||||
simply scm_frame_free (mem).
|
||||
This function calls 'free' on a given pointer when a dynwind context
|
||||
is left. Thus the call to scm_dynwind_unwind_handler above could be
|
||||
replaced with simply scm_dynwind_free (mem).
|
||||
|
||||
** New functions scm_c_call_with_blocked_asyncs and
|
||||
scm_c_call_with_unblocked_asyncs
|
||||
|
||||
Like scm_call_with_blocked_asyncs etc. but for C functions.
|
||||
|
||||
** New functions scm_frame_block_asyncs and scm_frame_unblock_asyncs
|
||||
** New functions scm_dynwind_block_asyncs and scm_dynwind_unblock_asyncs
|
||||
|
||||
In addition to scm_c_call_with_blocked_asyncs you can now also use
|
||||
scm_frame_block_asyncs in a 'frame' (see above). Likewise for
|
||||
scm_c_call_with_unblocked_asyncs and scm_frame_unblock_asyncs.
|
||||
scm_dynwind_block_asyncs in a 'dynwind context' (see above). Likewise for
|
||||
scm_c_call_with_unblocked_asyncs and scm_dynwind_unblock_asyncs.
|
||||
|
||||
** The macros SCM_DEFER_INTS, SCM_ALLOW_INTS, SCM_REDEFER_INTS,
|
||||
SCM_REALLOW_INTS have been deprecated.
|
||||
|
||||
They do no longer fulfill their original role of blocking signal
|
||||
delivery. Depending on what you want to achieve, replace a pair of
|
||||
SCM_DEFER_INTS and SCM_ALLOW_INTS with a frame that locks a mutex,
|
||||
blocks asyncs, or both. See node "Critical Sections" in the manual.
|
||||
SCM_DEFER_INTS and SCM_ALLOW_INTS with a dynwind context that locks a
|
||||
mutex, blocks asyncs, or both. See node "Critical Sections" in the
|
||||
manual.
|
||||
|
||||
** The value 'scm_mask_ints' is no longer writable.
|
||||
|
||||
|
@ -1065,12 +1066,12 @@ scm_c_call_with_unblocked_asyncs instead.
|
|||
|
||||
** New way to temporarily set the current input, output or error ports
|
||||
|
||||
C code can now use scm_frame_current_<foo>_port in a 'frame' (see
|
||||
above). <foo> is one of "input", "output" or "error".
|
||||
C code can now use scm_dynwind_current_<foo>_port in a 'dynwind
|
||||
conetxt' (see above). <foo> is one of "input", "output" or "error".
|
||||
|
||||
** New way to temporarily set fluids
|
||||
|
||||
C code can now use scm_frame_fluid in a 'frame' (see
|
||||
C code can now use scm_dynwind_fluid in a 'dynwind context' (see
|
||||
above) to temporarily set the value of a fluid.
|
||||
|
||||
** New types scm_t_intmax and scm_t_uintmax.
|
||||
|
|
|
@ -1,9 +1,13 @@
|
|||
2006-01-29 Marius Vollmer <mvo@zagadka.de>
|
||||
|
||||
Renamed the "frames" that are related to dynamic-wind to "dynamic
|
||||
contexts. Renamed all functions from scm_frame_ to scm_dynwind_.
|
||||
Updated documentation.
|
||||
|
||||
2005-12-19 Ludovic Courtès <ludovic.courtes@laas.fr>
|
||||
|
||||
* api-data.texi (Operations Related to Symbols):
|
||||
Documented `scm_take_locale_symbol ()'.
|
||||
|
||||
|
||||
2005-12-15 Kevin Ryde <user42@zip.com.au>
|
||||
|
||||
|
|
|
@ -2326,21 +2326,22 @@ error is signalled.
|
|||
the danger of a deadlock. In a multi-threaded program, you will need
|
||||
additional synchronization to avoid modifying reserved arrays.)
|
||||
|
||||
You must take care to always unreserve an array after reserving it, also
|
||||
in the presence of non-local exits. To simplify this, reserving and
|
||||
unreserving work like a frame (@pxref{Frames}): a call to
|
||||
@code{scm_array_get_handle} can be thought of as beginning a frame and
|
||||
@code{scm_array_handle_release} as ending it. When a non-local exit
|
||||
happens between these two calls, the array is implicitely unreserved.
|
||||
You must take care to always unreserve an array after reserving it,
|
||||
also in the presence of non-local exits. To simplify this, reserving
|
||||
and unreserving work like a dynwind context (@pxref{Dynamic Wind}): a
|
||||
call to @code{scm_array_get_handle} can be thought of as beginning a
|
||||
dynwind context and @code{scm_array_handle_release} as ending it.
|
||||
When a non-local exit happens between these two calls, the array is
|
||||
implicitely unreserved.
|
||||
|
||||
That is, you need to properly pair reserving and unreserving in your
|
||||
code, but you don't need to worry about non-local exits.
|
||||
|
||||
These calls and other pairs of calls that establish dynamic contexts
|
||||
need to be properly nested. If you begin a frame prior to reserving an
|
||||
array, you need to unreserve the array before ending the frame.
|
||||
Likewise, when reserving two or more arrays in a certain order, you need
|
||||
to unreserve them in the opposite order.
|
||||
These calls and other pairs of calls that establish dynwind contexts
|
||||
need to be properly nested. If you begin a context prior to reserving
|
||||
an array, you need to unreserve the array before ending the context.
|
||||
Likewise, when reserving two or more arrays in a certain order, you
|
||||
need to unreserve them in the opposite order.
|
||||
|
||||
Once you have reserved an array and have retrieved the pointer to its
|
||||
elements, you must figure out the layout of the elements in memory.
|
||||
|
@ -2356,11 +2357,11 @@ indices. The scalar position then is the offset of the element with the
|
|||
given indices from the start of the storage block of the array.
|
||||
|
||||
In Guile, this mapping function is restricted to be @dfn{affine}: all
|
||||
mapping function of Guile arrays can be written as @code{p = b +
|
||||
mapping functions of Guile arrays can be written as @code{p = b +
|
||||
c[0]*i[0] + c[1]*i[1] + ... + c[n-1]*i[n-1]} where @code{i[k]} is the
|
||||
@nicode{k}th index and @code{n} is the rank of the array. For example,
|
||||
a matrix of size 3x3 would have @code{b == 0}, @code{c[0] == 3} and
|
||||
@code{c[1] == 1}. When you transpose this matrix (with
|
||||
@nicode{k}th index and @code{n} is the rank of the array. For
|
||||
example, a matrix of size 3x3 would have @code{b == 0}, @code{c[0] ==
|
||||
3} and @code{c[1] == 1}. When you transpose this matrix (with
|
||||
@code{transpose-array}, say), you will get an array whose mapping
|
||||
function has @code{b == 0}, @code{c[0] == 1} and @code{c[1] == 3}.
|
||||
|
||||
|
|
|
@ -20,8 +20,7 @@ flow of Scheme affects C code.
|
|||
* Multiple Values:: Returning and accepting multiple values.
|
||||
* Exceptions:: Throwing and catching exceptions.
|
||||
* Error Reporting:: Procedures for signaling errors.
|
||||
* Dynamic Wind:: Guarding against non-local entrance/exit.
|
||||
* Frames:: Another way to handle non-localness
|
||||
* Dynamic Wind:: Dealing with non-local entrance/exit.
|
||||
* Handling Errors:: How to handle errors in C code.
|
||||
@end menu
|
||||
|
||||
|
@ -463,8 +462,7 @@ flow going on as normal.
|
|||
|
||||
@code{dynamic-wind} (@pxref{Dynamic Wind}) can be used to ensure setup
|
||||
and cleanup code is run when a program locus is resumed or abandoned
|
||||
through the continuation mechanism. C code can use @dfn{frames}
|
||||
(@pxref{Frames}).
|
||||
through the continuation mechanism.
|
||||
|
||||
@sp 1
|
||||
Continuations are a powerful mechanism, and can be used to implement
|
||||
|
@ -1013,6 +1011,71 @@ if an exception occurs then @code{#f} is returned instead.
|
|||
@node Dynamic Wind
|
||||
@subsection Dynamic Wind
|
||||
|
||||
For Scheme code, the fundamental procedure to react to non-local entry
|
||||
and exits of dynamic contexts is @code{dynamic-wind}. C code could
|
||||
use @code{scm_internal_dynamic_wind}, but since C does not allow the
|
||||
convenient construction of anonymous procedures that close over
|
||||
lexical variables, this will be, well, inconvenient.
|
||||
|
||||
Therefore, Guile offers the functions @code{scm_dynwind_begin} and
|
||||
@code{scm_dynwind_end} to delimit a dynamic extent. Within this
|
||||
dynamic extent, which is calles a @dfn{dynwind context}, you can
|
||||
perform various @dfn{dynwind actions} that control what happens when
|
||||
the dynwind context is entered or left. For example, you can register
|
||||
a cleanup routine with @code{scm_dynwind_unwind_handler} that is
|
||||
executed when the context is left. There are several other more
|
||||
specialized dynwind actions as well, for example to temporarily block
|
||||
the execution of asyncs or to temporarily change the current output
|
||||
port. They are described elsewhere in this manual.
|
||||
|
||||
Here is an example that shows how to prevent memory leaks.
|
||||
|
||||
@example
|
||||
|
||||
/* Suppose there is a function called FOO in some library that you
|
||||
would like to make available to Scheme code (or to C code that
|
||||
follows the Scheme conventions).
|
||||
|
||||
FOO takes two C strings and returns a new string. When an error has
|
||||
occurred in FOO, it returns NULL.
|
||||
*/
|
||||
|
||||
char *foo (char *s1, char *s2);
|
||||
|
||||
/* SCM_FOO interfaces the C function FOO to the Scheme way of life.
|
||||
It takes care to free up all temporary strings in the case of
|
||||
non-local exits.
|
||||
*/
|
||||
|
||||
SCM
|
||||
scm_foo (SCM s1, SCM s2)
|
||||
@{
|
||||
char *c_s1, *c_s2, *c_res;
|
||||
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
c_s1 = scm_to_locale_string (s1);
|
||||
|
||||
/* Call 'free (c_s1)' when the dynwind context is left.
|
||||
*/
|
||||
scm_dynwind_unwind_handler (free, c_s1, SCM_F_WIND_EXPLICITLY);
|
||||
|
||||
c_s2 = scm_to_locale_string (s2);
|
||||
|
||||
/* Same as above, but more concisely.
|
||||
*/
|
||||
scm_dynwind_free (c_s2);
|
||||
|
||||
c_res = foo (c_s1, c_s2);
|
||||
if (c_res == NULL)
|
||||
scm_memory_error ("foo");
|
||||
|
||||
scm_dynwind_end ();
|
||||
|
||||
return scm_take_locale_string (res);
|
||||
@}
|
||||
@end example
|
||||
|
||||
@rnindex dynamic-wind
|
||||
@deffn {Scheme Procedure} dynamic-wind in_guard thunk out_guard
|
||||
@deffnx {C Function} scm_dynamic_wind (in_guard, thunk, out_guard)
|
||||
|
@ -1066,95 +1129,29 @@ a-cont
|
|||
@end lisp
|
||||
@end deffn
|
||||
|
||||
@node Frames
|
||||
@subsection Frames
|
||||
|
||||
For Scheme code, the fundamental procedure to react to non-local entry
|
||||
and exits of dynamic contexts is @code{dynamic-wind}. C code could use
|
||||
@code{scm_internal_dynamic_wind}, but since C does not allow the
|
||||
convenient construction of anonymous procedures that close over lexical
|
||||
variables, this will be, well, inconvenient. Instead, C code can use
|
||||
@dfn{frames}.
|
||||
|
||||
Guile offers the functions @code{scm_frame_begin} and
|
||||
@code{scm_frame_end} to delimit a dynamic extent. Within this dynamic
|
||||
extent, which is called a @dfn{frame}, you can perform various
|
||||
@dfn{frame actions} that control what happens when the frame is entered
|
||||
or left. For example, you can register a cleanup routine with
|
||||
@code{scm_frame_unwind} that is executed when the frame is left. There are
|
||||
several other more specialized frame actions as well, for example to
|
||||
temporarily block the execution of asyncs or to temporarily change the
|
||||
current output port. They are described elsewhere in this manual.
|
||||
|
||||
Here is an example that shows how to prevent memory leaks.
|
||||
|
||||
@example
|
||||
|
||||
/* Suppose there is a function called FOO in some library that you
|
||||
would like to make available to Scheme code (or to C code that
|
||||
follows the Scheme conventions).
|
||||
|
||||
FOO takes two C strings and returns a new string. When an error has
|
||||
occurred in FOO, it returns NULL.
|
||||
*/
|
||||
|
||||
char *foo (char *s1, char *s2);
|
||||
|
||||
/* SCM_FOO interfaces the C function FOO to the Scheme way of life.
|
||||
It takes care to free up all temporary strings in the case of
|
||||
non-local exits.
|
||||
*/
|
||||
|
||||
SCM
|
||||
scm_foo (SCM s1, SCM s2)
|
||||
@{
|
||||
char *c_s1, *c_s2, *c_res;
|
||||
|
||||
scm_frame_begin (0);
|
||||
|
||||
c_s1 = scm_to_locale_string (s1);
|
||||
|
||||
/* Call 'free (c_s1)' when the frame is left.
|
||||
*/
|
||||
scm_frame_unwind_handler (free, c_s1, SCM_F_WIND_EXPLICITLY);
|
||||
|
||||
c_s2 = scm_to_locale_string (s2);
|
||||
|
||||
/* Same as above, but more concisely.
|
||||
*/
|
||||
scm_frame_free (c_s2);
|
||||
|
||||
c_res = foo (c_s1, c_s2);
|
||||
if (c_res == NULL)
|
||||
scm_memory_error ("foo");
|
||||
|
||||
scm_frame_end ();
|
||||
|
||||
return scm_take_locale_string (res);
|
||||
@}
|
||||
@end example
|
||||
|
||||
@deftp {C Type} scm_t_frame_flags
|
||||
@deftp {C Type} scm_t_dynwind_flags
|
||||
This is an enumeration of several flags that modify the behavior of
|
||||
@code{scm_begin_frame}. The flags are listed in the following table.
|
||||
@code{scm_dynwind_begin}. The flags are listed in the following
|
||||
table.
|
||||
|
||||
@table @code
|
||||
@item SCM_F_FRAME_REWINDABLE
|
||||
The frame is @dfn{rewindable}. This means that it can be reentered
|
||||
non-locally (via the invokation of a continuation). The default is that
|
||||
a frame can not be reentered non-locally.
|
||||
@item SCM_F_DYNWIND_REWINDABLE
|
||||
The dynamic context is @dfn{rewindable}. This means that it can be
|
||||
reentered non-locally (via the invokation of a continuation). The
|
||||
default is that a dynwind context can not be reentered non-locally.
|
||||
@end table
|
||||
|
||||
@end deftp
|
||||
|
||||
@deftypefn {C Function} void scm_frame_begin (scm_t_frame_flags flags)
|
||||
The function @code{scm_begin_frame} starts a new frame and makes it the
|
||||
`current' one.
|
||||
@deftypefn {C Function} void scm_dynwind_begin (scm_t_dynwind_flags flags)
|
||||
The function @code{scm_dynwind_begin} starts a new dynamic context and
|
||||
makes it the `current' one.
|
||||
|
||||
The @var{flags} argument determines the default behavior of the frame.
|
||||
For normal frames, use 0. This will result in a frame that can not be
|
||||
reentered with a captured continuation. When you are prepared to handle
|
||||
reentries, include @code{SCM_F_FRAME_REWINDABLE} in @var{flags}.
|
||||
The @var{flags} argument determines the default behavior of the
|
||||
context. Normally, use 0. This will result in a context that can not
|
||||
be reentered with a captured continuation. When you are prepared to
|
||||
handle reentries, include @code{SCM_F_DYNWIND_REWINDABLE} in
|
||||
@var{flags}.
|
||||
|
||||
Being prepared for reentry means that the effects of unwind handlers
|
||||
can be undone on reentry. In the example above, we want to prevent a
|
||||
|
@ -1163,51 +1160,54 @@ frees the memory. But once the memory is freed, we can not get it
|
|||
back on reentry. Thus reentry can not be allowed.
|
||||
|
||||
The consequence is that continuations become less useful when
|
||||
non-reenterable frames are captured, but you don't need to worry about
|
||||
that too much.
|
||||
non-reenterable contexts are captured, but you don't need to worry
|
||||
about that too much.
|
||||
|
||||
The frame is ended either implicitly when a non-local exit happens, or
|
||||
explicitly with @code{scm_end_frame}. You must make sure that a frame
|
||||
is indeed ended properly. If you fail to call @code{scm_end_frame}
|
||||
for each @code{scm_begin_frame}, the behavior is undefined.
|
||||
The context is ended either implicitly when a non-local exit happens,
|
||||
or explicitly with @code{scm_dynwind_end}. You must make sure that a
|
||||
dynwind context is indeed ended properly. If you fail to call
|
||||
@code{scm_dynwind_end} for each @code{scm_dynwind_begin}, the behavior
|
||||
is undefined.
|
||||
@end deftypefn
|
||||
|
||||
@deftypefn {C Function} void scm_frame_end ()
|
||||
End the current frame explicitly and make the previous frame current.
|
||||
@deftypefn {C Function} void scm_dynwind_end ()
|
||||
End the current dynamic context explicitly and make the previous one
|
||||
current.
|
||||
@end deftypefn
|
||||
|
||||
@deftp {C Type} scm_t_wind_flags
|
||||
This is an enumeration of several flags that modify the behavior of
|
||||
@code{scm_on_unwind_handler} and @code{scm_on_rewind_handler}. The
|
||||
flags are listed in the following table.
|
||||
@code{scm_dynwind_unwind_handler} and
|
||||
@code{scm_dynwind_rewind_handler}. The flags are listed in the
|
||||
following table.
|
||||
|
||||
@table @code
|
||||
@item SCM_F_WIND_EXPLICITLY
|
||||
@vindex SCM_F_WIND_EXPLICITLY
|
||||
The registered action is also carried out when the frame is entered or
|
||||
left locally.
|
||||
The registered action is also carried out when the dynwind context is
|
||||
entered or left locally.
|
||||
@end table
|
||||
@end deftp
|
||||
|
||||
@deftypefn {C Function} void scm_frame_unwind_handler (void (*func)(void *), void *data, scm_t_wind_flags flags)
|
||||
@deftypefnx {C Function} void scm_frame_unwind_handler_with_scm (void (*func)(SCM), SCM data, scm_t_wind_flags flags)
|
||||
@deftypefn {C Function} void scm_dynwind_unwind_handler (void (*func)(void *), void *data, scm_t_wind_flags flags)
|
||||
@deftypefnx {C Function} void scm_dynwind_unwind_handler_with_scm (void (*func)(SCM), SCM data, scm_t_wind_flags flags)
|
||||
Arranges for @var{func} to be called with @var{data} as its arguments
|
||||
when the current frame ends implicitly. If @var{flags} contains
|
||||
@code{SCM_F_WIND_EXPLICITLY}, @var{func} is also called when the frame
|
||||
ends explicitly with @code{scm_frame_end}.
|
||||
when the current context ends implicitly. If @var{flags} contains
|
||||
@code{SCM_F_WIND_EXPLICITLY}, @var{func} is also called when the
|
||||
context ends explicitly with @code{scm_dynwind_end}.
|
||||
|
||||
The function @code{scm_frame_unwind_handler_with_scm} takes care that
|
||||
The function @code{scm_dynwind_unwind_handler_with_scm} takes care that
|
||||
@var{data} is protected from garbage collection.
|
||||
@end deftypefn
|
||||
|
||||
@deftypefn {C Function} void scm_frame_rewind_handler (void (*func)(void *), void *data, scm_t_wind_flags flags)
|
||||
@deftypefnx {C Function} void scm_frame_rewind_handler_with_scm (void (*func)(SCM), SCM data, scm_t_wind_flags flags)
|
||||
@deftypefn {C Function} void scm_dynwind_rewind_handler (void (*func)(void *), void *data, scm_t_wind_flags flags)
|
||||
@deftypefnx {C Function} void scm_dynwind_rewind_handler_with_scm (void (*func)(SCM), SCM data, scm_t_wind_flags flags)
|
||||
Arrange for @var{func} to be called with @var{data} as its argument when
|
||||
the current frame is restarted by rewinding the stack. When @var{flags}
|
||||
the current context is restarted by rewinding the stack. When @var{flags}
|
||||
contains @code{SCM_F_WIND_EXPLICITLY}, @var{func} is called immediately
|
||||
as well.
|
||||
|
||||
The function @code{scm_frame_rewind_handler_with_scm} takes care that
|
||||
The function @code{scm_dynwind_rewind_handler_with_scm} takes care that
|
||||
@var{data} is protected from garbage collection.
|
||||
@end deftypefn
|
||||
|
||||
|
|
|
@ -3603,8 +3603,8 @@ listed in this section, you are `future-proof'.
|
|||
Converting a Scheme string to a C string will often allocate fresh
|
||||
memory to hold the result. You must take care that this memory is
|
||||
properly freed eventually. In many cases, this can be achieved by
|
||||
using @code{scm_frame_free} inside an appropriate frame,
|
||||
@xref{Frames}.
|
||||
using @code{scm_dynwind_free} inside an appropriate dynwind context,
|
||||
@xref{Dynamic Wind}.
|
||||
|
||||
@deftypefn {C Function} SCM scm_from_locale_string (const char *str)
|
||||
@deftypefnx {C Function} SCM scm_from_locale_stringn (const char *str, size_t len)
|
||||
|
@ -3632,7 +3632,8 @@ can then use @var{str} directly as its internal representation.
|
|||
@deftypefnx {C Function} {char *} scm_to_locale_stringn (SCM str, size_t *lenp)
|
||||
Returns a C string in the current locale encoding with the same
|
||||
contents as @var{str}. The C string must be freed with @code{free}
|
||||
eventually, maybe by using @code{scm_frame_free}, @xref{Frames}.
|
||||
eventually, maybe by using @code{scm_dynwind_free}, @xref{Dynamic
|
||||
Wind}.
|
||||
|
||||
For @code{scm_to_locale_string}, the returned string is
|
||||
null-terminated and an error is signalled when @var{str} contains
|
||||
|
|
|
@ -670,16 +670,16 @@ Change the ports returned by @code{current-input-port},
|
|||
so that they use the supplied @var{port} for input or output.
|
||||
@end deffn
|
||||
|
||||
@deftypefn {C Function} void scm_frame_current_input_port (SCM port)
|
||||
@deftypefnx {C Function} void scm_frame_current_output_port (SCM port)
|
||||
@deftypefnx {C Function} void scm_frame_current_error_port (SCM port)
|
||||
@deftypefn {C Function} void scm_dynwind_current_input_port (SCM port)
|
||||
@deftypefnx {C Function} void scm_dynwind_current_output_port (SCM port)
|
||||
@deftypefnx {C Function} void scm_dynwind_current_error_port (SCM port)
|
||||
These functions must be used inside a pair of calls to
|
||||
@code{scm_frame_begin} and @code{scm_frame_end} (@pxref{Frames}).
|
||||
During the dynamic extent of the frame, the indicated port is set to
|
||||
@code{scm_dynwind_begin} and @code{scm_dynwind_end} (@pxref{Dynamic
|
||||
Wind}). During the dynwind context, the indicated port is set to
|
||||
@var{port}.
|
||||
|
||||
More precisely, the current port is swapped with a `backup' value
|
||||
whenever the frame is entered or left. The backup value is
|
||||
whenever the dynwind context is entered or left. The backup value is
|
||||
initialized with the @var{port} argument.
|
||||
@end deftypefn
|
||||
|
||||
|
|
|
@ -124,8 +124,8 @@ in place of @code{realloc} when appropriate, and @code{scm_gc_calloc}
|
|||
and @code{scm_calloc}, to be used in place of @code{calloc} when
|
||||
appropriate.
|
||||
|
||||
The function @code{scm_frame_free} can be useful when memory should be
|
||||
freed when a frame is left, @xref{Frames}.
|
||||
The function @code{scm_dynwind_free} can be useful when memory should
|
||||
be freed when a dynwind context, @xref{Dynamic Wind}.
|
||||
|
||||
For really specialized needs, take at look at
|
||||
@code{scm_gc_register_collectable_memory} and
|
||||
|
|
|
@ -115,9 +115,9 @@ them temporarily.
|
|||
|
||||
In addition to the C versions of @code{call-with-blocked-asyncs} and
|
||||
@code{call-with-unblocked-asyncs}, C code can use
|
||||
@code{scm_frame_block_asyncs} and @code{scm_frame_unblock_asyncs}
|
||||
inside a @dfn{frame} (@pxref{Frames}) to block or unblock system asyncs
|
||||
temporarily.
|
||||
@code{scm_dynwind_block_asyncs} and @code{scm_dynwind_unblock_asyncs}
|
||||
inside a @dfn{dynamic context} (@pxref{Dynamic Wind}) to block or
|
||||
unblock system asyncs temporarily.
|
||||
|
||||
@deffn {Scheme Procedure} system-async-mark proc [thread]
|
||||
@deffnx {C Function} scm_system_async_mark (proc)
|
||||
|
@ -159,16 +159,16 @@ returned by @var{proc}. For the first two variants, call @var{proc}
|
|||
with no arguments; for the third, call it with @var{data}.
|
||||
@end deffn
|
||||
|
||||
@deftypefn {C Function} void scm_frame_block_asyncs ()
|
||||
@deftypefn {C Function} void scm_dynwind_block_asyncs ()
|
||||
This function must be used inside a pair of calls to
|
||||
@code{scm_frame_begin} and @code{scm_frame_end} (@pxref{Frames}).
|
||||
During the dynamic extent of the frame, asyncs are blocked by one level.
|
||||
@code{scm_dynwind_begin} and @code{scm_dynwind_end} (@pxref{Dynamic
|
||||
Wind}). During the dynwind context, asyncs are blocked by one level.
|
||||
@end deftypefn
|
||||
|
||||
@deftypefn {C Function} void scm_frame_unblock_asyncs ()
|
||||
@deftypefn {C Function} void scm_dynwind_unblock_asyncs ()
|
||||
This function must be used inside a pair of calls to
|
||||
@code{scm_frame_begin} and @code{scm_frame_end} (@pxref{Frames}).
|
||||
During the dynamic extent of the frame, asyncs are unblocked by one
|
||||
@code{scm_dynwind_begin} and @code{scm_dynwind_end} (@pxref{Dynamic
|
||||
Wind}). During the dynwind context, asyncs are unblocked by one
|
||||
level.
|
||||
@end deftypefn
|
||||
|
||||
|
@ -355,9 +355,9 @@ blocked in @code{lock-mutex}, the wait is interrupted and the async is
|
|||
executed. When the async returns, the wait resumes.
|
||||
@end deffn
|
||||
|
||||
@deftypefn {C Function} void scm_frame_lock_mutex (SCM mutex)
|
||||
Arrange for @var{mutex} to be locked whenever the current frame is
|
||||
entered and to be unlocked when it is exited.
|
||||
@deftypefn {C Function} void scm_dynwind_lock_mutex (SCM mutex)
|
||||
Arrange for @var{mutex} to be locked whenever the current dynwind
|
||||
context is entered and to be unlocked when it is exited.
|
||||
@end deftypefn
|
||||
|
||||
@deffn {Scheme Procedure} try-mutex mx
|
||||
|
@ -523,16 +523,16 @@ This means that no non-local exit (such as a signalled error) might
|
|||
happen, for example.
|
||||
@end deffn
|
||||
|
||||
@deftypefn {C Function} void scm_frame_critical_section (SCM mutex)
|
||||
Call @code{scm_frame_lock_mutex} on @var{mutex} and call
|
||||
@code{scm_frame_block_asyncs}. When @var{mutex} is false, a recursive
|
||||
@deftypefn {C Function} void scm_dynwind_critical_section (SCM mutex)
|
||||
Call @code{scm_dynwind_lock_mutex} on @var{mutex} and call
|
||||
@code{scm_dynwind_block_asyncs}. When @var{mutex} is false, a recursive
|
||||
mutex provided by Guile is used instead.
|
||||
|
||||
The effect of a call to @code{scm_frame_critical_section} is that the
|
||||
current frame (@pxref{Frames}) turns into a critical section. Because
|
||||
of the locked mutex, no second thread can enter it concurrently and
|
||||
because of the blocked asyncs, no system async can reenter it from the
|
||||
current thread.
|
||||
The effect of a call to @code{scm_dynwind_critical_section} is that
|
||||
the current dynwind context (@pxref{Dynamic Wind}) turns into a
|
||||
critical section. Because of the locked mutex, no second thread can
|
||||
enter it concurrently and because of the blocked asyncs, no system
|
||||
async can reenter it from the current thread.
|
||||
|
||||
When the current thread reenters the critical section anyway, the kind
|
||||
of @var{mutex} determines what happens: When @var{mutex} is recursive,
|
||||
|
@ -633,15 +633,15 @@ The function @code{scm_c_with_fluid} is similar but only allows one
|
|||
fluid to be set instead of a list.
|
||||
@end deftypefn
|
||||
|
||||
@deftypefn {C Function} void scm_frame_fluid (SCM fluid, SCM val)
|
||||
@deftypefn {C Function} void scm_dynwind_fluid (SCM fluid, SCM val)
|
||||
This function must be used inside a pair of calls to
|
||||
@code{scm_frame_begin} and @code{scm_frame_end} (@pxref{Frames}).
|
||||
During the dynamic extent of the frame, the fluid @var{fluid} is set
|
||||
to @var{val}.
|
||||
@code{scm_dynwind_begin} and @code{scm_dynwind_end} (@pxref{Dynamic
|
||||
Wind}). During the dynwind context, the fluid @var{fluid} is set to
|
||||
@var{val}.
|
||||
|
||||
More precisely, the value of the fluid is swapped with a `backup'
|
||||
value whenever the frame is entered or left. The backup value is
|
||||
initialized with the @var{val} argument.
|
||||
value whenever the dynwind context is entered or left. The backup
|
||||
value is initialized with the @var{val} argument.
|
||||
@end deftypefn
|
||||
|
||||
@deffn {Scheme Procedure} make-dynamic-state [parent]
|
||||
|
@ -678,9 +678,9 @@ Call @var{proc} while @var{state} is the current dynamic
|
|||
state object.
|
||||
@end deffn
|
||||
|
||||
@deftypefn {C Procedure} void scm_frame_current_dynamic_state (SCM state)
|
||||
Set the current dynamic state to @var{state} for the dynamic extent of
|
||||
the current frame.
|
||||
@deftypefn {C Procedure} void scm_dynwind_current_dynamic_state (SCM state)
|
||||
Set the current dynamic state to @var{state} for the current dynwind
|
||||
context.
|
||||
@end deftypefn
|
||||
|
||||
@deftypefn {C Procedure} {void *} scm_c_with_dynamic_state (SCM state, void *(*func)(void *), void *data)
|
||||
|
|
|
@ -377,11 +377,11 @@ its previous value when @code{with-output-to-port} returns normally or
|
|||
when it is exited non-locally. Likewise, the port needs to be set again
|
||||
when control enters non-locally.
|
||||
|
||||
Scheme code can use the @code{dynamic-wind} function to arrange for the
|
||||
setting and resetting of the global state. C code could use the
|
||||
corresponding @code{scm_internal_dynamic_wind} function, but it might
|
||||
prefer to use the @dfn{frames} concept that is more natural for C code,
|
||||
(@pxref{Frames}).
|
||||
Scheme code can use the @code{dynamic-wind} function to arrange for
|
||||
the setting and resetting of the global state. C code can use the
|
||||
corresponding @code{scm_internal_dynamic_wind} function, or a
|
||||
@code{scm_dynwind_begin}/@code{scm_dynwind_end} pair together with
|
||||
suitable 'dynwind actions' (@pxref{Dynamic Wind}).
|
||||
|
||||
Instead of coping with non-local control flow, you can also prevent it
|
||||
by erecting a @emph{continuation barrier}, @xref{Continuation
|
||||
|
@ -407,7 +407,7 @@ including a non-local exit although @code{scm_cons} would not ordinarily
|
|||
do such a thing on its own.
|
||||
|
||||
If you do not want to allow the running of asynchronous signal handlers,
|
||||
you can block them temporarily with @code{scm_frame_block_asyncs}, for
|
||||
you can block them temporarily with @code{scm_dynwind_block_asyncs}, for
|
||||
example. See @xref{System asyncs}.
|
||||
|
||||
Since signal handling in Guile relies on safe points, you need to make
|
||||
|
@ -602,8 +602,8 @@ section via recursive function calls.
|
|||
Guile provides two mechanisms to support critical sections as outlined
|
||||
above. You can either use the macros
|
||||
@code{SCM_CRITICAL_SECTION_START} and @code{SCM_CRITICAL_SECTION_END}
|
||||
for very simple sections; or use a frame together with a call to
|
||||
@code{scm_frame_critical_section}.
|
||||
for very simple sections; or use a dynwind context together with a
|
||||
call to @code{scm_dynwind_critical_section}.
|
||||
|
||||
The macros only work reliably for critical sections that are
|
||||
guaranteed to not cause a non-local exit. They also do not detect an
|
||||
|
@ -612,7 +612,7 @@ only use them to delimit critical sections that do not contain calls
|
|||
to libguile functions or to other external functions that might do
|
||||
complicated things.
|
||||
|
||||
The function @code{scm_frame_critical_section}, on the other hand,
|
||||
will correctly deal with non-local exits because it requires a frame.
|
||||
Also, by using a separate mutex for each critical section, it can
|
||||
detect accidental reentries.
|
||||
The function @code{scm_dynwind_critical_section}, on the other hand,
|
||||
will correctly deal with non-local exits because it requires a dynwind
|
||||
context. Also, by using a separate mutex for each critical section,
|
||||
it can detect accidental reentries.
|
||||
|
|
|
@ -1,3 +1,9 @@
|
|||
2006-01-29 Marius Vollmer <mvo@zagadka.de>
|
||||
|
||||
Renamed the "frames" that are related to dynamic-wind to "dynamic
|
||||
contexts. Renamed all functions from scm_frame_ to scm_dynwind_.
|
||||
Updated documentation.
|
||||
|
||||
2006-01-28 Marius Vollmer <mvo@zagadka.de>
|
||||
|
||||
* inline.h, pairs.c (scm_is_pair): Moved scm_is_pair from pairs.c
|
||||
|
|
|
@ -454,22 +454,22 @@ scm_c_call_with_unblocked_asyncs (void *(*proc) (void *data), void *data)
|
|||
}
|
||||
|
||||
void
|
||||
scm_frame_block_asyncs ()
|
||||
scm_dynwind_block_asyncs ()
|
||||
{
|
||||
scm_i_thread *t = SCM_I_CURRENT_THREAD;
|
||||
scm_frame_rewind_handler (increase_block, t, SCM_F_WIND_EXPLICITLY);
|
||||
scm_frame_unwind_handler (decrease_block, t, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_rewind_handler (increase_block, t, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_unwind_handler (decrease_block, t, SCM_F_WIND_EXPLICITLY);
|
||||
}
|
||||
|
||||
void
|
||||
scm_frame_unblock_asyncs ()
|
||||
scm_dynwind_unblock_asyncs ()
|
||||
{
|
||||
scm_i_thread *t = SCM_I_CURRENT_THREAD;
|
||||
if (t->block_asyncs == 0)
|
||||
scm_misc_error ("scm_with_unblocked_asyncs",
|
||||
"asyncs already unblocked", SCM_EOL);
|
||||
scm_frame_rewind_handler (decrease_block, t, SCM_F_WIND_EXPLICITLY);
|
||||
scm_frame_unwind_handler (increase_block, t, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_rewind_handler (decrease_block, t, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_unwind_handler (increase_block, t, SCM_F_WIND_EXPLICITLY);
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -48,8 +48,8 @@ SCM_API SCM scm_call_with_blocked_asyncs (SCM proc);
|
|||
SCM_API SCM scm_call_with_unblocked_asyncs (SCM proc);
|
||||
void *scm_c_call_with_blocked_asyncs (void *(*p) (void *d), void *d);
|
||||
void *scm_c_call_with_unblocked_asyncs (void *(*p) (void *d), void *d);
|
||||
void scm_frame_block_asyncs (void);
|
||||
void scm_frame_unblock_asyncs (void);
|
||||
void scm_dynwind_block_asyncs (void);
|
||||
void scm_dynwind_unblock_asyncs (void);
|
||||
|
||||
/* Critical sections */
|
||||
|
||||
|
|
|
@ -56,8 +56,8 @@ SCM_DEFINE (scm_debug_options, "debug-options-interface", 0, 1, 0,
|
|||
{
|
||||
SCM ans;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_frame_critical_section (SCM_BOOL_F);
|
||||
scm_dynwind_begin (0);
|
||||
scm_dynwind_critical_section (SCM_BOOL_F);
|
||||
|
||||
ans = scm_options (setting, scm_debug_opts, SCM_N_DEBUG_OPTIONS, FUNC_NAME);
|
||||
if (!(1 <= SCM_N_FRAMES && SCM_N_FRAMES <= SCM_MAX_FRAME_SIZE))
|
||||
|
@ -69,7 +69,7 @@ SCM_DEFINE (scm_debug_options, "debug-options-interface", 0, 1, 0,
|
|||
scm_stack_checking_enabled_p = SCM_STACK_CHECKING_P;
|
||||
scm_debug_eframe_size = 2 * SCM_N_FRAMES;
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return ans;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
|
|
@ -153,11 +153,11 @@ SCM_DEFINE (scm_dynamic_link, "dynamic-link", 1, 0, 0,
|
|||
void *handle;
|
||||
char *file;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
file = scm_to_locale_string (filename);
|
||||
scm_frame_free (file);
|
||||
scm_dynwind_free (file);
|
||||
handle = sysdep_dynl_link (file, FUNC_NAME);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
SCM_RETURN_NEWSMOB2 (scm_tc16_dynamic_obj, SCM_UNPACK (filename), handle);
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -222,12 +222,12 @@ SCM_DEFINE (scm_dynamic_func, "dynamic-func", 2, 0, 0,
|
|||
} else {
|
||||
char *chars;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
chars = scm_to_locale_string (name);
|
||||
scm_frame_free (chars);
|
||||
scm_dynwind_free (chars);
|
||||
func = (void (*) ()) sysdep_dynl_func (chars, DYNL_HANDLE (dobj),
|
||||
FUNC_NAME);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return scm_from_ulong ((unsigned long) func);
|
||||
}
|
||||
}
|
||||
|
@ -290,7 +290,7 @@ SCM_DEFINE (scm_dynamic_args_call, "dynamic-args-call", 3, 0, 0,
|
|||
int result, argc;
|
||||
char **argv;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
if (scm_is_string (func))
|
||||
func = scm_dynamic_func (func, dobj);
|
||||
|
@ -298,13 +298,13 @@ SCM_DEFINE (scm_dynamic_args_call, "dynamic-args-call", 3, 0, 0,
|
|||
fptr = (int (*) (int, char **)) scm_to_ulong (func);
|
||||
|
||||
argv = scm_i_allocate_string_pointers (args);
|
||||
scm_frame_unwind_handler (free_string_pointers, argv,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_unwind_handler (free_string_pointers, argv,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
for (argc = 0; argv[argc]; argc++)
|
||||
;
|
||||
result = (*fptr) (argc, argv);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return scm_from_int (result);
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
|
|
@ -120,11 +120,11 @@ scm_internal_dynamic_wind (scm_t_guard before,
|
|||
{
|
||||
SCM ans;
|
||||
|
||||
scm_frame_begin (SCM_F_FRAME_REWINDABLE);
|
||||
scm_frame_rewind_handler (before, guard_data, SCM_F_WIND_EXPLICITLY);
|
||||
scm_frame_unwind_handler (after, guard_data, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_begin (SCM_F_DYNWIND_REWINDABLE);
|
||||
scm_dynwind_rewind_handler (before, guard_data, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_unwind_handler (after, guard_data, SCM_F_WIND_EXPLICITLY);
|
||||
ans = inner (inner_data);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return ans;
|
||||
}
|
||||
|
||||
|
@ -149,17 +149,17 @@ static scm_t_bits tc16_winder;
|
|||
#define WINDER_MARK_P(w) (SCM_SMOB_FLAGS(w) & WINDER_F_MARK)
|
||||
|
||||
void
|
||||
scm_frame_begin (scm_t_frame_flags flags)
|
||||
scm_dynwind_begin (scm_t_dynwind_flags flags)
|
||||
{
|
||||
SCM f;
|
||||
SCM_NEWSMOB (f, tc16_frame, 0);
|
||||
if (flags & SCM_F_FRAME_REWINDABLE)
|
||||
if (flags & SCM_F_DYNWIND_REWINDABLE)
|
||||
SCM_SET_SMOB_FLAGS (f, FRAME_F_REWINDABLE);
|
||||
scm_i_set_dynwinds (scm_cons (f, scm_i_dynwinds ()));
|
||||
}
|
||||
|
||||
void
|
||||
scm_frame_end (void)
|
||||
scm_dynwind_end (void)
|
||||
{
|
||||
SCM winds;
|
||||
|
||||
|
@ -195,8 +195,8 @@ winder_mark (SCM w)
|
|||
}
|
||||
|
||||
void
|
||||
scm_frame_unwind_handler (void (*proc) (void *), void *data,
|
||||
scm_t_wind_flags flags)
|
||||
scm_dynwind_unwind_handler (void (*proc) (void *), void *data,
|
||||
scm_t_wind_flags flags)
|
||||
{
|
||||
SCM w;
|
||||
SCM_NEWSMOB2 (w, tc16_winder, (scm_t_bits) proc, (scm_t_bits) data);
|
||||
|
@ -206,8 +206,8 @@ scm_frame_unwind_handler (void (*proc) (void *), void *data,
|
|||
}
|
||||
|
||||
void
|
||||
scm_frame_rewind_handler (void (*proc) (void *), void *data,
|
||||
scm_t_wind_flags flags)
|
||||
scm_dynwind_rewind_handler (void (*proc) (void *), void *data,
|
||||
scm_t_wind_flags flags)
|
||||
{
|
||||
SCM w;
|
||||
SCM_NEWSMOB2 (w, tc16_winder, (scm_t_bits) proc, (scm_t_bits) data);
|
||||
|
@ -218,8 +218,8 @@ scm_frame_rewind_handler (void (*proc) (void *), void *data,
|
|||
}
|
||||
|
||||
void
|
||||
scm_frame_unwind_handler_with_scm (void (*proc) (SCM), SCM data,
|
||||
scm_t_wind_flags flags)
|
||||
scm_dynwind_unwind_handler_with_scm (void (*proc) (SCM), SCM data,
|
||||
scm_t_wind_flags flags)
|
||||
{
|
||||
SCM w;
|
||||
scm_t_bits fl = ((flags&SCM_F_WIND_EXPLICITLY)? WINDER_F_EXPLICIT : 0);
|
||||
|
@ -229,8 +229,8 @@ scm_frame_unwind_handler_with_scm (void (*proc) (SCM), SCM data,
|
|||
}
|
||||
|
||||
void
|
||||
scm_frame_rewind_handler_with_scm (void (*proc) (SCM), SCM data,
|
||||
scm_t_wind_flags flags)
|
||||
scm_dynwind_rewind_handler_with_scm (void (*proc) (SCM), SCM data,
|
||||
scm_t_wind_flags flags)
|
||||
{
|
||||
SCM w;
|
||||
SCM_NEWSMOB2 (w, tc16_winder, (scm_t_bits) proc, SCM_UNPACK (data));
|
||||
|
@ -241,9 +241,9 @@ scm_frame_rewind_handler_with_scm (void (*proc) (SCM), SCM data,
|
|||
}
|
||||
|
||||
void
|
||||
scm_frame_free (void *mem)
|
||||
scm_dynwind_free (void *mem)
|
||||
{
|
||||
scm_frame_unwind_handler (free, mem, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_unwind_handler (free, mem, SCM_F_WIND_EXPLICITLY);
|
||||
}
|
||||
|
||||
#ifdef GUILE_DEBUG
|
||||
|
|
|
@ -43,27 +43,27 @@ SCM_API void scm_init_dynwind (void);
|
|||
SCM_API void scm_swap_bindings (SCM vars, SCM vals);
|
||||
|
||||
typedef enum {
|
||||
SCM_F_FRAME_REWINDABLE = (1 << 0)
|
||||
} scm_t_frame_flags;
|
||||
SCM_F_DYNWIND_REWINDABLE = (1 << 0)
|
||||
} scm_t_dynwind_flags;
|
||||
|
||||
typedef enum {
|
||||
SCM_F_WIND_EXPLICITLY = (1 << 0)
|
||||
} scm_t_wind_flags;
|
||||
|
||||
SCM_API void scm_frame_begin (scm_t_frame_flags);
|
||||
SCM_API void scm_frame_end (void);
|
||||
SCM_API void scm_dynwind_begin (scm_t_dynwind_flags);
|
||||
SCM_API void scm_dynwind_end (void);
|
||||
|
||||
SCM_API void scm_frame_unwind_handler (void (*func) (void *), void *data,
|
||||
scm_t_wind_flags);
|
||||
SCM_API void scm_frame_rewind_handler (void (*func) (void *), void *data,
|
||||
scm_t_wind_flags);
|
||||
SCM_API void scm_dynwind_unwind_handler (void (*func) (void *), void *data,
|
||||
scm_t_wind_flags);
|
||||
SCM_API void scm_dynwind_rewind_handler (void (*func) (void *), void *data,
|
||||
scm_t_wind_flags);
|
||||
|
||||
SCM_API void scm_frame_unwind_handler_with_scm (void (*func) (SCM), SCM data,
|
||||
scm_t_wind_flags);
|
||||
SCM_API void scm_frame_rewind_handler_with_scm (void (*func) (SCM), SCM data,
|
||||
scm_t_wind_flags);
|
||||
SCM_API void scm_dynwind_unwind_handler_with_scm (void (*func) (SCM), SCM data,
|
||||
scm_t_wind_flags);
|
||||
SCM_API void scm_dynwind_rewind_handler_with_scm (void (*func) (SCM), SCM data,
|
||||
scm_t_wind_flags);
|
||||
|
||||
SCM_API void scm_frame_free (void *mem);
|
||||
SCM_API void scm_dynwind_free (void *mem);
|
||||
|
||||
#ifdef GUILE_DEBUG
|
||||
SCM_API SCM scm_wind_chain (void);
|
||||
|
|
|
@ -130,12 +130,12 @@ SCM_DEFINE (scm_strerror, "strerror", 1, 0, 0,
|
|||
#define FUNC_NAME s_scm_strerror
|
||||
{
|
||||
SCM ret;
|
||||
scm_frame_begin (0);
|
||||
scm_i_frame_pthread_mutex_lock (&scm_i_misc_mutex);
|
||||
scm_dynwind_begin (0);
|
||||
scm_i_dynwind_pthread_mutex_lock (&scm_i_misc_mutex);
|
||||
|
||||
ret = scm_from_locale_string (SCM_I_STRERROR (scm_to_int (err)));
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return ret;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
|
|
@ -3099,14 +3099,14 @@ SCM_DEFINE (scm_eval_options_interface, "eval-options-interface", 0, 1, 0,
|
|||
{
|
||||
SCM ans;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_frame_critical_section (SCM_BOOL_F);
|
||||
scm_dynwind_begin (0);
|
||||
scm_dynwind_critical_section (SCM_BOOL_F);
|
||||
ans = scm_options (setting,
|
||||
scm_eval_opts,
|
||||
SCM_N_EVAL_OPTIONS,
|
||||
FUNC_NAME);
|
||||
scm_eval_stack = SCM_EVAL_STACK * sizeof (void *);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
|
||||
return ans;
|
||||
}
|
||||
|
@ -5908,15 +5908,15 @@ scm_eval_x (SCM exp, SCM module_or_state)
|
|||
{
|
||||
SCM res;
|
||||
|
||||
scm_frame_begin (SCM_F_FRAME_REWINDABLE);
|
||||
scm_dynwind_begin (SCM_F_DYNWIND_REWINDABLE);
|
||||
if (scm_is_dynamic_state (module_or_state))
|
||||
scm_frame_current_dynamic_state (module_or_state);
|
||||
scm_dynwind_current_dynamic_state (module_or_state);
|
||||
else
|
||||
scm_frame_current_module (module_or_state);
|
||||
scm_dynwind_current_module (module_or_state);
|
||||
|
||||
res = scm_primitive_eval_x (exp);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return res;
|
||||
}
|
||||
|
||||
|
@ -5934,15 +5934,15 @@ SCM_DEFINE (scm_eval, "eval", 2, 0, 0,
|
|||
{
|
||||
SCM res;
|
||||
|
||||
scm_frame_begin (SCM_F_FRAME_REWINDABLE);
|
||||
scm_dynwind_begin (SCM_F_DYNWIND_REWINDABLE);
|
||||
if (scm_is_dynamic_state (module_or_state))
|
||||
scm_frame_current_dynamic_state (module_or_state);
|
||||
scm_dynwind_current_dynamic_state (module_or_state);
|
||||
else
|
||||
scm_frame_current_module (module_or_state);
|
||||
scm_dynwind_current_module (module_or_state);
|
||||
|
||||
res = scm_primitive_eval (exp);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return res;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
|
|
@ -77,12 +77,12 @@ load_extension (SCM lib, SCM init)
|
|||
extension_t *ext;
|
||||
char *clib, *cinit;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
clib = scm_to_locale_string (lib);
|
||||
scm_frame_free (clib);
|
||||
scm_dynwind_free (clib);
|
||||
cinit = scm_to_locale_string (init);
|
||||
scm_frame_free (cinit);
|
||||
scm_dynwind_free (cinit);
|
||||
|
||||
for (ext = registered_extensions; ext; ext = ext->next)
|
||||
if ((ext->lib == NULL || !strcmp (ext->lib, clib))
|
||||
|
@ -92,7 +92,7 @@ load_extension (SCM lib, SCM init)
|
|||
break;
|
||||
}
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
}
|
||||
|
||||
/* Dynamically link the library. */
|
||||
|
|
|
@ -194,13 +194,13 @@
|
|||
do { \
|
||||
int eno; \
|
||||
char *cstr1, *cstr2; \
|
||||
scm_frame_begin (0); \
|
||||
scm_dynwind_begin (0); \
|
||||
cstr1 = scm_to_locale_string (str1); \
|
||||
scm_frame_free (cstr1); \
|
||||
scm_dynwind_free (cstr1); \
|
||||
cstr2 = scm_to_locale_string (str2); \
|
||||
scm_frame_free (cstr2); \
|
||||
scm_dynwind_free (cstr2); \
|
||||
SCM_SYSCALL (code); \
|
||||
eno = errno; scm_frame_end (); errno = eno; \
|
||||
eno = errno; scm_dynwind_end (); errno = eno; \
|
||||
} while (0)
|
||||
|
||||
|
||||
|
@ -1384,10 +1384,10 @@ SCM_DEFINE (scm_readlink, "readlink", 1, 0, 0,
|
|||
SCM result;
|
||||
char *c_path;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
c_path = scm_to_locale_string (path);
|
||||
scm_frame_free (c_path);
|
||||
scm_dynwind_free (c_path);
|
||||
|
||||
buf = scm_malloc (size);
|
||||
|
||||
|
@ -1406,7 +1406,7 @@ SCM_DEFINE (scm_readlink, "readlink", 1, 0, 0,
|
|||
}
|
||||
result = scm_take_locale_stringn (buf, rv);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return result;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -1449,12 +1449,12 @@ SCM_DEFINE (scm_copy_file, "copy-file", 2, 0, 0,
|
|||
char buf[BUFSIZ];
|
||||
struct stat oldstat;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
c_oldfile = scm_to_locale_string (oldfile);
|
||||
scm_frame_free (c_oldfile);
|
||||
scm_dynwind_free (c_oldfile);
|
||||
c_newfile = scm_to_locale_string (newfile);
|
||||
scm_frame_free (c_newfile);
|
||||
scm_dynwind_free (c_newfile);
|
||||
|
||||
oldfd = open (c_oldfile, O_RDONLY);
|
||||
if (oldfd == -1)
|
||||
|
@ -1489,7 +1489,7 @@ SCM_DEFINE (scm_copy_file, "copy-file", 2, 0, 0,
|
|||
if (close (newfd) == -1)
|
||||
SCM_SYSERROR;
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return SCM_UNSPECIFIED;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
|
|
@ -199,8 +199,8 @@ next_fluid_num ()
|
|||
{
|
||||
size_t n;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_i_frame_pthread_mutex_lock (&fluid_admin_mutex);
|
||||
scm_dynwind_begin (0);
|
||||
scm_i_dynwind_pthread_mutex_lock (&fluid_admin_mutex);
|
||||
|
||||
if ((allocated_fluids_len > 0) &&
|
||||
(allocated_fluids_num == allocated_fluids_len))
|
||||
|
@ -248,7 +248,7 @@ next_fluid_num ()
|
|||
allocated_fluids_num += 1;
|
||||
allocated_fluids[n] = 1;
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return n;
|
||||
}
|
||||
|
||||
|
@ -420,13 +420,13 @@ scm_c_with_fluids (SCM fluids, SCM values, SCM (*cproc) (), void *cdata)
|
|||
cproc, cdata);
|
||||
|
||||
data = scm_cons (fluids, values);
|
||||
scm_frame_begin (SCM_F_FRAME_REWINDABLE);
|
||||
scm_frame_rewind_handler_with_scm (swap_fluids, data,
|
||||
scm_dynwind_begin (SCM_F_DYNWIND_REWINDABLE);
|
||||
scm_dynwind_rewind_handler_with_scm (swap_fluids, data,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
scm_frame_unwind_handler_with_scm (swap_fluids_reverse, data,
|
||||
scm_dynwind_unwind_handler_with_scm (swap_fluids_reverse, data,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
ans = cproc (cdata);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return ans;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -448,10 +448,10 @@ scm_c_with_fluid (SCM fluid, SCM value, SCM (*cproc) (), void *cdata)
|
|||
{
|
||||
SCM ans;
|
||||
|
||||
scm_frame_begin (SCM_F_FRAME_REWINDABLE);
|
||||
scm_frame_fluid (fluid, value);
|
||||
scm_dynwind_begin (SCM_F_DYNWIND_REWINDABLE);
|
||||
scm_dynwind_fluid (fluid, value);
|
||||
ans = cproc (cdata);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return ans;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -466,11 +466,11 @@ swap_fluid (SCM data)
|
|||
}
|
||||
|
||||
void
|
||||
scm_frame_fluid (SCM fluid, SCM value)
|
||||
scm_dynwind_fluid (SCM fluid, SCM value)
|
||||
{
|
||||
SCM data = scm_cons (fluid, value);
|
||||
scm_frame_rewind_handler_with_scm (swap_fluid, data, SCM_F_WIND_EXPLICITLY);
|
||||
scm_frame_unwind_handler_with_scm (swap_fluid, data, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_rewind_handler_with_scm (swap_fluid, data, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_unwind_handler_with_scm (swap_fluid, data, SCM_F_WIND_EXPLICITLY);
|
||||
}
|
||||
|
||||
SCM
|
||||
|
@ -558,13 +558,13 @@ swap_dynamic_state (SCM loc)
|
|||
}
|
||||
|
||||
void
|
||||
scm_frame_current_dynamic_state (SCM state)
|
||||
scm_dynwind_current_dynamic_state (SCM state)
|
||||
{
|
||||
SCM loc = scm_cons (state, SCM_EOL);
|
||||
scm_assert_smob_type (tc16_dynamic_state, state);
|
||||
scm_frame_rewind_handler_with_scm (swap_dynamic_state, loc,
|
||||
scm_dynwind_rewind_handler_with_scm (swap_dynamic_state, loc,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
scm_frame_unwind_handler_with_scm (swap_dynamic_state, loc,
|
||||
scm_dynwind_unwind_handler_with_scm (swap_dynamic_state, loc,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
}
|
||||
|
||||
|
@ -572,10 +572,10 @@ void *
|
|||
scm_c_with_dynamic_state (SCM state, void *(*func)(void *), void *data)
|
||||
{
|
||||
void *result;
|
||||
scm_frame_begin (SCM_F_FRAME_REWINDABLE);
|
||||
scm_frame_current_dynamic_state (state);
|
||||
scm_dynwind_begin (SCM_F_DYNWIND_REWINDABLE);
|
||||
scm_dynwind_current_dynamic_state (state);
|
||||
result = func (data);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return result;
|
||||
}
|
||||
|
||||
|
@ -586,10 +586,10 @@ SCM_DEFINE (scm_with_dynamic_state, "with-dynamic-state", 2, 0, 0,
|
|||
#define FUNC_NAME s_scm_with_dynamic_state
|
||||
{
|
||||
SCM result;
|
||||
scm_frame_begin (SCM_F_FRAME_REWINDABLE);
|
||||
scm_frame_current_dynamic_state (state);
|
||||
scm_dynwind_begin (SCM_F_DYNWIND_REWINDABLE);
|
||||
scm_dynwind_current_dynamic_state (state);
|
||||
result = scm_call_0 (proc);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return result;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
|
|
@ -70,14 +70,14 @@ SCM_API SCM scm_c_with_fluid (SCM fluid, SCM val,
|
|||
SCM_API SCM scm_with_fluids (SCM fluids, SCM vals, SCM thunk);
|
||||
SCM_API SCM scm_with_fluid (SCM fluid, SCM val, SCM thunk);
|
||||
|
||||
SCM_API void scm_frame_fluid (SCM fluid, SCM value);
|
||||
SCM_API void scm_dynwind_fluid (SCM fluid, SCM value);
|
||||
|
||||
SCM_API SCM scm_make_dynamic_state (SCM parent);
|
||||
SCM_API SCM scm_dynamic_state_p (SCM obj);
|
||||
SCM_API int scm_is_dynamic_state (SCM obj);
|
||||
SCM_API SCM scm_current_dynamic_state (void);
|
||||
SCM_API SCM scm_set_current_dynamic_state (SCM state);
|
||||
SCM_API void scm_frame_current_dynamic_state (SCM state);
|
||||
SCM_API void scm_dynwind_current_dynamic_state (SCM state);
|
||||
SCM_API void *scm_c_with_dynamic_state (SCM state,
|
||||
void *(*func)(void *), void *data);
|
||||
SCM_API SCM scm_with_dynamic_state (SCM state, SCM proc);
|
||||
|
|
|
@ -293,13 +293,13 @@ SCM_DEFINE (scm_open_file, "open-file", 2, 0, 0,
|
|||
char *md;
|
||||
char *ptr;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
file = scm_to_locale_string (filename);
|
||||
scm_frame_free (file);
|
||||
scm_dynwind_free (file);
|
||||
|
||||
md = scm_to_locale_string (mode);
|
||||
scm_frame_free (md);
|
||||
scm_dynwind_free (md);
|
||||
|
||||
switch (*md)
|
||||
{
|
||||
|
@ -347,7 +347,7 @@ SCM_DEFINE (scm_open_file, "open-file", 2, 0, 0,
|
|||
}
|
||||
port = scm_i_fdes_to_port (fdes, scm_i_mode_bits (mode), filename);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
|
||||
return port;
|
||||
}
|
||||
|
|
|
@ -94,10 +94,10 @@ SCM_DEFINE (scm_gettext, "gettext", 1, 2, 0,
|
|||
char const *c_result;
|
||||
SCM result;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
c_msgid = scm_to_locale_string (msgid);
|
||||
scm_frame_free (c_msgid);
|
||||
scm_dynwind_free (c_msgid);
|
||||
|
||||
if (SCM_UNBNDP (domain))
|
||||
{
|
||||
|
@ -109,7 +109,7 @@ SCM_DEFINE (scm_gettext, "gettext", 1, 2, 0,
|
|||
char *c_domain;
|
||||
|
||||
c_domain = scm_to_locale_string (domain);
|
||||
scm_frame_free (c_domain);
|
||||
scm_dynwind_free (c_domain);
|
||||
|
||||
if (SCM_UNBNDP (category))
|
||||
{
|
||||
|
@ -131,7 +131,7 @@ SCM_DEFINE (scm_gettext, "gettext", 1, 2, 0,
|
|||
else
|
||||
result = scm_from_locale_string (c_result);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return result;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -152,13 +152,13 @@ SCM_DEFINE (scm_ngettext, "ngettext", 3, 2, 0,
|
|||
const char *c_result;
|
||||
SCM result;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
c_msgid = scm_to_locale_string (msgid);
|
||||
scm_frame_free (c_msgid);
|
||||
scm_dynwind_free (c_msgid);
|
||||
|
||||
c_msgid_plural = scm_to_locale_string (msgid_plural);
|
||||
scm_frame_free (c_msgid_plural);
|
||||
scm_dynwind_free (c_msgid_plural);
|
||||
|
||||
c_n = scm_to_ulong (n);
|
||||
|
||||
|
@ -172,7 +172,7 @@ SCM_DEFINE (scm_ngettext, "ngettext", 3, 2, 0,
|
|||
char *c_domain;
|
||||
|
||||
c_domain = scm_to_locale_string (domain);
|
||||
scm_frame_free (c_domain);
|
||||
scm_dynwind_free (c_domain);
|
||||
|
||||
if (SCM_UNBNDP (category))
|
||||
{
|
||||
|
@ -197,7 +197,7 @@ SCM_DEFINE (scm_ngettext, "ngettext", 3, 2, 0,
|
|||
else
|
||||
result = scm_from_locale_string (c_result);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return result;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -213,14 +213,14 @@ SCM_DEFINE (scm_textdomain, "textdomain", 0, 1, 0,
|
|||
char *c_domain;
|
||||
SCM result = SCM_BOOL_F;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
if (SCM_UNBNDP (domainname))
|
||||
c_domain = NULL;
|
||||
else
|
||||
{
|
||||
c_domain = scm_to_locale_string (domainname);
|
||||
scm_frame_free (c_domain);
|
||||
scm_dynwind_free (c_domain);
|
||||
}
|
||||
|
||||
c_result = textdomain (c_domain);
|
||||
|
@ -229,7 +229,7 @@ SCM_DEFINE (scm_textdomain, "textdomain", 0, 1, 0,
|
|||
else if (!SCM_UNBNDP (domainname))
|
||||
SCM_SYSERROR;
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return result;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -246,18 +246,18 @@ SCM_DEFINE (scm_bindtextdomain, "bindtextdomain", 1, 1, 0,
|
|||
char const *c_result;
|
||||
SCM result;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
if (SCM_UNBNDP (directory))
|
||||
c_directory = NULL;
|
||||
else
|
||||
{
|
||||
c_directory = scm_to_locale_string (directory);
|
||||
scm_frame_free (c_directory);
|
||||
scm_dynwind_free (c_directory);
|
||||
}
|
||||
|
||||
c_domain = scm_to_locale_string (domainname);
|
||||
scm_frame_free (c_domain);
|
||||
scm_dynwind_free (c_domain);
|
||||
|
||||
c_result = bindtextdomain (c_domain, c_directory);
|
||||
|
||||
|
@ -268,7 +268,7 @@ SCM_DEFINE (scm_bindtextdomain, "bindtextdomain", 1, 1, 0,
|
|||
else
|
||||
result = SCM_BOOL_F;
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return result;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -285,18 +285,18 @@ SCM_DEFINE (scm_bind_textdomain_codeset, "bind-textdomain-codeset", 1, 1, 0,
|
|||
char const *c_result;
|
||||
SCM result;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
if (SCM_UNBNDP (encoding))
|
||||
c_encoding = NULL;
|
||||
else
|
||||
{
|
||||
c_encoding = scm_to_locale_string (encoding);
|
||||
scm_frame_free (c_encoding);
|
||||
scm_dynwind_free (c_encoding);
|
||||
}
|
||||
|
||||
c_domain = scm_to_locale_string (domainname);
|
||||
scm_frame_free (c_domain);
|
||||
scm_dynwind_free (c_domain);
|
||||
|
||||
c_result = bind_textdomain_codeset (c_domain, c_encoding);
|
||||
|
||||
|
@ -307,7 +307,7 @@ SCM_DEFINE (scm_bind_textdomain_codeset, "bind-textdomain-codeset", 1, 1, 0,
|
|||
else
|
||||
result = SCM_BOOL_F;
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return result;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
|
|
@ -103,7 +103,7 @@ SCM_DEFINE (scm_make_list, "make-list", 1, 1, 0,
|
|||
"Create a list containing of @var{n} elements, where each\n"
|
||||
"element is initialized to @var{init}. @var{init} defaults to\n"
|
||||
"the empty list @code{()} if not given.")
|
||||
#define FUNC_NAME s_scm_srfi1_count
|
||||
#define FUNC_NAME s_scm_make_list
|
||||
{
|
||||
unsigned nn = scm_to_uint (n);
|
||||
unsigned i;
|
||||
|
|
|
@ -88,8 +88,8 @@ SCM_DEFINE (scm_primitive_load, "primitive-load", 1, 0, 0,
|
|||
|
||||
{ /* scope */
|
||||
SCM port = scm_open_file (filename, scm_from_locale_string ("r"));
|
||||
scm_frame_begin (SCM_F_FRAME_REWINDABLE);
|
||||
scm_i_frame_current_load_port (port);
|
||||
scm_dynwind_begin (SCM_F_DYNWIND_REWINDABLE);
|
||||
scm_i_dynwind_current_load_port (port);
|
||||
|
||||
while (1)
|
||||
{
|
||||
|
@ -109,7 +109,7 @@ SCM_DEFINE (scm_primitive_load, "primitive-load", 1, 0, 0,
|
|||
scm_primitive_eval_x (form);
|
||||
}
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
scm_close_port (port);
|
||||
}
|
||||
return SCM_UNSPECIFIED;
|
||||
|
@ -316,11 +316,11 @@ SCM_DEFINE (scm_search_path, "search-path", 2, 1, 0,
|
|||
if (SCM_UNBNDP (extensions))
|
||||
extensions = SCM_EOL;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
filename_chars = scm_to_locale_string (filename);
|
||||
filename_len = strlen (filename_chars);
|
||||
scm_frame_free (filename_chars);
|
||||
scm_dynwind_free (filename_chars);
|
||||
|
||||
/* If FILENAME is absolute, return it unchanged. */
|
||||
#ifdef __MINGW32__
|
||||
|
@ -334,7 +334,7 @@ SCM_DEFINE (scm_search_path, "search-path", 2, 1, 0,
|
|||
if (filename_len >= 1 && filename_chars[0] == '/')
|
||||
#endif
|
||||
{
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return filename;
|
||||
}
|
||||
|
||||
|
@ -371,7 +371,7 @@ SCM_DEFINE (scm_search_path, "search-path", 2, 1, 0,
|
|||
|
||||
buf.buf_len = 512;
|
||||
buf.buf = scm_malloc (buf.buf_len);
|
||||
scm_frame_unwind_handler (stringbuf_free, &buf, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_unwind_handler (stringbuf_free, &buf, SCM_F_WIND_EXPLICITLY);
|
||||
|
||||
/* Try every path element.
|
||||
*/
|
||||
|
@ -424,7 +424,7 @@ SCM_DEFINE (scm_search_path, "search-path", 2, 1, 0,
|
|||
scm_wrong_type_arg_msg (NULL, 0, path, "proper list");
|
||||
|
||||
end:
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return result;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
|
|
@ -92,9 +92,9 @@ scm_c_call_with_current_module (SCM module,
|
|||
}
|
||||
|
||||
void
|
||||
scm_frame_current_module (SCM module)
|
||||
scm_dynwind_current_module (SCM module)
|
||||
{
|
||||
scm_frame_fluid (the_module, module);
|
||||
scm_dynwind_fluid (the_module, module);
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
|
@ -69,7 +69,7 @@ SCM_API SCM scm_set_current_module (SCM module);
|
|||
|
||||
SCM_API SCM scm_c_call_with_current_module (SCM module,
|
||||
SCM (*func)(void *), void *data);
|
||||
SCM_API void scm_frame_current_module (SCM module);
|
||||
SCM_API void scm_dynwind_current_module (SCM module);
|
||||
|
||||
SCM_API SCM scm_c_lookup (const char *name);
|
||||
SCM_API SCM scm_c_define (const char *name, SCM val);
|
||||
|
|
|
@ -351,10 +351,10 @@ SCM_DEFINE (scm_getserv, "getserv", 0, 2, 0,
|
|||
return scm_return_entry (entry);
|
||||
}
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
protoname = scm_to_locale_string (protocol);
|
||||
scm_frame_free (protoname);
|
||||
scm_dynwind_free (protoname);
|
||||
|
||||
if (scm_is_string (name))
|
||||
{
|
||||
|
@ -372,7 +372,7 @@ SCM_DEFINE (scm_getserv, "getserv", 0, 2, 0,
|
|||
if (!entry)
|
||||
SCM_SYSERROR_MSG("no such service ~A", scm_list_1 (name), eno);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return scm_return_entry (entry);
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
|
|
@ -93,7 +93,7 @@ SCM_API int scm_i_pthread_key_create (scm_i_pthread_key_t *key,
|
|||
/* Convenience functions
|
||||
*/
|
||||
#define scm_i_scm_pthread_mutex_lock scm_i_pthread_mutex_lock
|
||||
#define scm_i_frame_pthread_mutex_lock scm_i_pthread_mutex_lock
|
||||
#define scm_i_dynwind_pthread_mutex_lock scm_i_pthread_mutex_lock
|
||||
#define scm_i_scm_pthread_cond_wait scm_i_pthread_cond_wait
|
||||
#define scm_i_scm_pthread_cond_timedwait scm_i_pthread_cond_timedwait
|
||||
|
||||
|
|
|
@ -436,38 +436,38 @@ SCM_DEFINE (scm_set_current_error_port, "set-current-error-port", 1, 0, 0,
|
|||
#undef FUNC_NAME
|
||||
|
||||
void
|
||||
scm_frame_current_input_port (SCM port)
|
||||
scm_dynwind_current_input_port (SCM port)
|
||||
#define FUNC_NAME NULL
|
||||
{
|
||||
SCM_VALIDATE_OPINPORT (1, port);
|
||||
scm_frame_fluid (cur_inport_fluid, port);
|
||||
scm_dynwind_fluid (cur_inport_fluid, port);
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
||||
void
|
||||
scm_frame_current_output_port (SCM port)
|
||||
scm_dynwind_current_output_port (SCM port)
|
||||
#define FUNC_NAME NULL
|
||||
{
|
||||
port = SCM_COERCE_OUTPORT (port);
|
||||
SCM_VALIDATE_OPOUTPORT (1, port);
|
||||
scm_frame_fluid (cur_outport_fluid, port);
|
||||
scm_dynwind_fluid (cur_outport_fluid, port);
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
||||
void
|
||||
scm_frame_current_error_port (SCM port)
|
||||
scm_dynwind_current_error_port (SCM port)
|
||||
#define FUNC_NAME NULL
|
||||
{
|
||||
port = SCM_COERCE_OUTPORT (port);
|
||||
SCM_VALIDATE_OPOUTPORT (1, port);
|
||||
scm_frame_fluid (cur_errport_fluid, port);
|
||||
scm_dynwind_fluid (cur_errport_fluid, port);
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
||||
void
|
||||
scm_i_frame_current_load_port (SCM port)
|
||||
scm_i_dynwind_current_load_port (SCM port)
|
||||
{
|
||||
scm_frame_fluid (cur_loadport_fluid, port);
|
||||
scm_dynwind_fluid (cur_loadport_fluid, port);
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -237,9 +237,9 @@ SCM_API SCM scm_current_load_port (void);
|
|||
SCM_API SCM scm_set_current_input_port (SCM port);
|
||||
SCM_API SCM scm_set_current_output_port (SCM port);
|
||||
SCM_API SCM scm_set_current_error_port (SCM port);
|
||||
SCM_API void scm_frame_current_input_port (SCM port);
|
||||
SCM_API void scm_frame_current_output_port (SCM port);
|
||||
SCM_API void scm_frame_current_error_port (SCM port);
|
||||
SCM_API void scm_dynwind_current_input_port (SCM port);
|
||||
SCM_API void scm_dynwind_current_output_port (SCM port);
|
||||
SCM_API void scm_dynwind_current_error_port (SCM port);
|
||||
SCM_API SCM scm_new_port_table_entry (scm_t_bits tag);
|
||||
SCM_API void scm_remove_from_port_table (SCM port);
|
||||
SCM_API void scm_grow_port_cbuf (SCM port, size_t requested);
|
||||
|
@ -306,7 +306,7 @@ SCM_API SCM scm_pt_member (SCM member);
|
|||
/* internal */
|
||||
|
||||
SCM_API long scm_i_mode_bits (SCM modes);
|
||||
SCM_API void scm_i_frame_current_load_port (SCM port);
|
||||
SCM_API void scm_i_dynwind_current_load_port (SCM port);
|
||||
|
||||
|
||||
#endif /* SCM_PORTS_H */
|
||||
|
|
|
@ -933,20 +933,20 @@ SCM_DEFINE (scm_execl, "execl", 1, 0, 1,
|
|||
char *exec_file;
|
||||
char **exec_argv;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
exec_file = scm_to_locale_string (filename);
|
||||
scm_frame_free (exec_file);
|
||||
scm_dynwind_free (exec_file);
|
||||
|
||||
exec_argv = scm_i_allocate_string_pointers (args);
|
||||
scm_frame_unwind_handler (free_string_pointers, exec_argv,
|
||||
scm_dynwind_unwind_handler (free_string_pointers, exec_argv,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
|
||||
execv (exec_file, exec_argv);
|
||||
SCM_SYSERROR;
|
||||
|
||||
/* not reached. */
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return SCM_BOOL_F;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -964,20 +964,20 @@ SCM_DEFINE (scm_execlp, "execlp", 1, 0, 1,
|
|||
char *exec_file;
|
||||
char **exec_argv;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
exec_file = scm_to_locale_string (filename);
|
||||
scm_frame_free (exec_file);
|
||||
scm_dynwind_free (exec_file);
|
||||
|
||||
exec_argv = scm_i_allocate_string_pointers (args);
|
||||
scm_frame_unwind_handler (free_string_pointers, exec_argv,
|
||||
scm_dynwind_unwind_handler (free_string_pointers, exec_argv,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
|
||||
execvp (exec_file, exec_argv);
|
||||
SCM_SYSERROR;
|
||||
|
||||
/* not reached. */
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return SCM_BOOL_F;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -999,24 +999,24 @@ SCM_DEFINE (scm_execle, "execle", 2, 0, 1,
|
|||
char **exec_env;
|
||||
char *exec_file;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
exec_file = scm_to_locale_string (filename);
|
||||
scm_frame_free (exec_file);
|
||||
scm_dynwind_free (exec_file);
|
||||
|
||||
exec_argv = scm_i_allocate_string_pointers (args);
|
||||
scm_frame_unwind_handler (free_string_pointers, exec_argv,
|
||||
scm_dynwind_unwind_handler (free_string_pointers, exec_argv,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
|
||||
exec_env = scm_i_allocate_string_pointers (env);
|
||||
scm_frame_unwind_handler (free_string_pointers, exec_env,
|
||||
scm_dynwind_unwind_handler (free_string_pointers, exec_env,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
|
||||
execve (exec_file, exec_argv, exec_env);
|
||||
SCM_SYSERROR;
|
||||
|
||||
/* not reached. */
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return SCM_BOOL_F;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -1147,10 +1147,10 @@ SCM_DEFINE (scm_mkstemp, "mkstemp!", 1, 0, 0,
|
|||
char *c_tmpl;
|
||||
int rv;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
c_tmpl = scm_to_locale_string (tmpl);
|
||||
scm_frame_free (c_tmpl);
|
||||
scm_dynwind_free (c_tmpl);
|
||||
|
||||
SCM_SYSCALL (rv = mkstemp (c_tmpl));
|
||||
if (rv == -1)
|
||||
|
@ -1160,7 +1160,7 @@ SCM_DEFINE (scm_mkstemp, "mkstemp!", 1, 0, 0,
|
|||
SCM_INUM0, scm_string_length (tmpl),
|
||||
tmpl, SCM_INUM0);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return scm_fdes_to_port (rv, "w+", tmpl);
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -1361,7 +1361,7 @@ SCM_DEFINE (scm_setlocale, "setlocale", 1, 1, 0,
|
|||
char *clocale;
|
||||
char *rv;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
if (SCM_UNBNDP (locale))
|
||||
{
|
||||
|
@ -1370,7 +1370,7 @@ SCM_DEFINE (scm_setlocale, "setlocale", 1, 1, 0,
|
|||
else
|
||||
{
|
||||
clocale = scm_to_locale_string (locale);
|
||||
scm_frame_free (clocale);
|
||||
scm_dynwind_free (clocale);
|
||||
}
|
||||
|
||||
rv = setlocale (scm_i_to_lc_category (category, 1), clocale);
|
||||
|
@ -1383,7 +1383,7 @@ SCM_DEFINE (scm_setlocale, "setlocale", 1, 1, 0,
|
|||
SCM_SYSERROR;
|
||||
}
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return scm_from_locale_string (rv);
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -1505,17 +1505,17 @@ SCM_DEFINE (scm_crypt, "crypt", 2, 0, 0,
|
|||
SCM ret;
|
||||
char *c_key, *c_salt;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_i_frame_pthread_mutex_lock (&scm_i_misc_mutex);
|
||||
scm_dynwind_begin (0);
|
||||
scm_i_dynwind_pthread_mutex_lock (&scm_i_misc_mutex);
|
||||
|
||||
c_key = scm_to_locale_string (key);
|
||||
scm_frame_free (c_key);
|
||||
scm_dynwind_free (c_key);
|
||||
c_salt = scm_to_locale_string (salt);
|
||||
scm_frame_free (c_salt);
|
||||
scm_dynwind_free (c_salt);
|
||||
|
||||
ret = scm_from_locale_string (crypt (c_key, c_salt));
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return ret;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
@ -1831,8 +1831,8 @@ SCM_DEFINE (scm_gethostname, "gethostname", 0, 0, 0,
|
|||
char *const p = scm_malloc (len);
|
||||
const int res = gethostname (p, len);
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_frame_unwind_handler (free, p, 0);
|
||||
scm_dynwind_begin (0);
|
||||
scm_dynwind_unwind_handler (free, p, 0);
|
||||
|
||||
#else
|
||||
|
||||
|
@ -1858,8 +1858,8 @@ SCM_DEFINE (scm_gethostname, "gethostname", 0, 0, 0,
|
|||
|
||||
p = scm_malloc (len);
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_frame_unwind_handler (free, p, 0);
|
||||
scm_dynwind_begin (0);
|
||||
scm_dynwind_unwind_handler (free, p, 0);
|
||||
|
||||
res = gethostname (p, len);
|
||||
while (res == -1 && errno == ENAMETOOLONG)
|
||||
|
@ -1878,7 +1878,7 @@ SCM_DEFINE (scm_gethostname, "gethostname", 0, 0, 0,
|
|||
const int save_errno = errno;
|
||||
|
||||
// No guile exceptions can occur before we have freed p's memory.
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
free (p);
|
||||
|
||||
errno = save_errno;
|
||||
|
@ -1890,7 +1890,7 @@ SCM_DEFINE (scm_gethostname, "gethostname", 0, 0, 0,
|
|||
const SCM name = scm_from_locale_string (p);
|
||||
|
||||
// No guile exceptions can occur before we have freed p's memory.
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
free (p);
|
||||
|
||||
return name;
|
||||
|
|
|
@ -79,7 +79,7 @@ extern pthread_mutexattr_t scm_i_pthread_mutexattr_recursive[1];
|
|||
/* Convenience functions
|
||||
*/
|
||||
#define scm_i_scm_pthread_mutex_lock scm_pthread_mutex_lock
|
||||
#define scm_i_frame_pthread_mutex_lock scm_frame_pthread_mutex_lock
|
||||
#define scm_i_dynwind_pthread_mutex_lock scm_dynwind_pthread_mutex_lock
|
||||
#define scm_i_scm_pthread_cond_wait scm_pthread_cond_wait
|
||||
#define scm_i_scm_pthread_cond_timedwait scm_pthread_cond_timedwait
|
||||
|
||||
|
|
|
@ -308,10 +308,10 @@ scm_ramapc (int (*cproc)(), SCM data, SCM ra0, SCM lra, const char *what)
|
|||
plvra = SCM_CDRLOC (*plvra);
|
||||
}
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
vinds = scm_malloc (sizeof(long) * SCM_I_ARRAY_NDIM (ra0));
|
||||
scm_frame_free (vinds);
|
||||
scm_dynwind_free (vinds);
|
||||
|
||||
for (k = 0; k <= kmax; k++)
|
||||
vinds[k] = SCM_I_ARRAY_DIMS (ra0)[k].lbnd;
|
||||
|
@ -340,7 +340,7 @@ scm_ramapc (int (*cproc)(), SCM data, SCM ra0, SCM lra, const char *what)
|
|||
}
|
||||
while (k >= 0);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
@ -1011,10 +1011,10 @@ SCM_DEFINE (scm_array_index_map_x, "array-index-map!", 2, 0, 0,
|
|||
if (kmax < 0)
|
||||
return scm_array_set_x (ra, scm_call_0 (proc), SCM_EOL);
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
vinds = scm_malloc (sizeof(long) * SCM_I_ARRAY_NDIM (ra));
|
||||
scm_frame_free (vinds);
|
||||
scm_dynwind_free (vinds);
|
||||
|
||||
for (k = 0; k <= kmax; k++)
|
||||
vinds[k] = SCM_I_ARRAY_DIMS (ra)[k].lbnd;
|
||||
|
@ -1046,7 +1046,7 @@ SCM_DEFINE (scm_array_index_map_x, "array-index-map!", 2, 0, 0,
|
|||
}
|
||||
while (k >= 0);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return SCM_UNSPECIFIED;
|
||||
}
|
||||
else if (scm_is_generalized_vector (ra))
|
||||
|
|
|
@ -116,14 +116,14 @@ scm_internal_cwdr (scm_t_catch_body body, void *body_data,
|
|||
old_winds = scm_i_dynwinds ();
|
||||
scm_dowinds (SCM_EOL, scm_ilength (old_winds));
|
||||
|
||||
scm_frame_begin (SCM_F_FRAME_REWINDABLE);
|
||||
scm_frame_current_dynamic_state (scm_make_dynamic_state (SCM_UNDEFINED));
|
||||
scm_dynwind_begin (SCM_F_DYNWIND_REWINDABLE);
|
||||
scm_dynwind_current_dynamic_state (scm_make_dynamic_state (SCM_UNDEFINED));
|
||||
|
||||
my_handler_data.run_handler = 0;
|
||||
answer = scm_i_with_continuation_barrier (body, body_data,
|
||||
cwdr_handler, &my_handler_data);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
|
||||
/* Enter caller's dynamic state.
|
||||
*/
|
||||
|
|
|
@ -127,12 +127,12 @@ SCM_DEFINE (scm_system_star, "system*", 0, 0, 1,
|
|||
int pid;
|
||||
char **execargv;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
/* allocate before fork */
|
||||
execargv = scm_i_allocate_string_pointers (args);
|
||||
scm_frame_unwind_handler (free_string_pointers, execargv,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_unwind_handler (free_string_pointers, execargv,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
|
||||
/* make sure the child can't kill us (as per normal system call) */
|
||||
sig_ign = scm_from_long ((unsigned long) SIG_IGN);
|
||||
|
@ -148,7 +148,7 @@ SCM_DEFINE (scm_system_star, "system*", 0, 0, 1,
|
|||
execvp (execargv[0], execargv);
|
||||
SCM_SYSERROR;
|
||||
/* not reached. */
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return SCM_BOOL_F;
|
||||
}
|
||||
else
|
||||
|
@ -165,7 +165,7 @@ SCM_DEFINE (scm_system_star, "system*", 0, 0, 1,
|
|||
scm_sigaction (sigint, SCM_CAR (oldint), SCM_CDR (oldint));
|
||||
scm_sigaction (sigquit, SCM_CAR (oldquit), SCM_CDR (oldquit));
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return scm_from_int (status);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -828,10 +828,10 @@ scm_fill_sockaddr (int fam, SCM address, SCM *args, int which_arg,
|
|||
int addr_size;
|
||||
char *c_address;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
c_address = scm_to_locale_string (address);
|
||||
scm_frame_free (c_address);
|
||||
scm_dynwind_free (c_address);
|
||||
|
||||
/* the static buffer size in sockaddr_un seems to be arbitrary
|
||||
and not necessarily a hard limit. e.g., the glibc manual
|
||||
|
@ -847,7 +847,7 @@ scm_fill_sockaddr (int fam, SCM address, SCM *args, int which_arg,
|
|||
strcpy (soka->sun_path, c_address);
|
||||
*size = SUN_LEN (soka);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return (struct sockaddr *) soka;
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -525,14 +525,14 @@ SCM_DEFINE (scm_mktime, "mktime", 1, 1, 0,
|
|||
char **oldenv;
|
||||
int err;
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
bdtime2c (sbd_time, <, SCM_ARG1, FUNC_NAME);
|
||||
#if HAVE_STRUCT_TM_TM_ZONE
|
||||
scm_frame_free ((char *)lt.tm_zone);
|
||||
scm_dynwind_free ((char *)lt.tm_zone);
|
||||
#endif
|
||||
|
||||
scm_frame_critical_section (SCM_BOOL_F);
|
||||
scm_dynwind_critical_section (SCM_BOOL_F);
|
||||
|
||||
oldenv = setzone (zone, SCM_ARG2, FUNC_NAME);
|
||||
#ifdef LOCALTIME_CACHE
|
||||
|
@ -589,7 +589,7 @@ SCM_DEFINE (scm_mktime, "mktime", 1, 1, 0,
|
|||
if (zname)
|
||||
free (zname);
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return result;
|
||||
}
|
||||
#undef FUNC_NAME
|
||||
|
|
|
@ -964,11 +964,11 @@ scm_i_allocate_string_pointers (SCM list)
|
|||
if (len < 0)
|
||||
scm_wrong_type_arg_msg (NULL, 0, list, "proper list");
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
|
||||
result = (char **) scm_malloc ((len + 1) * sizeof (char *));
|
||||
result[len] = NULL;
|
||||
scm_frame_unwind_handler (free, result, 0);
|
||||
scm_dynwind_unwind_handler (free, result, 0);
|
||||
|
||||
/* The list might be have been modified in another thread, so
|
||||
we check LIST before each access.
|
||||
|
@ -979,7 +979,7 @@ scm_i_allocate_string_pointers (SCM list)
|
|||
list = SCM_CDR (list);
|
||||
}
|
||||
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return result;
|
||||
}
|
||||
|
||||
|
|
|
@ -998,12 +998,12 @@ SCM_DEFINE (scm_lock_mutex, "lock-mutex", 1, 0, 0,
|
|||
#undef FUNC_NAME
|
||||
|
||||
void
|
||||
scm_frame_lock_mutex (SCM mutex)
|
||||
scm_dynwind_lock_mutex (SCM mutex)
|
||||
{
|
||||
scm_frame_unwind_handler_with_scm ((void(*)(SCM))scm_unlock_mutex, mutex,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
scm_frame_rewind_handler_with_scm ((void(*)(SCM))scm_lock_mutex, mutex,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_unwind_handler_with_scm ((void(*)(SCM))scm_unlock_mutex, mutex,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_rewind_handler_with_scm ((void(*)(SCM))scm_lock_mutex, mutex,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
}
|
||||
|
||||
static char *
|
||||
|
@ -1403,10 +1403,10 @@ unlock (void *data)
|
|||
}
|
||||
|
||||
void
|
||||
scm_frame_pthread_mutex_lock (scm_i_pthread_mutex_t *mutex)
|
||||
scm_dynwind_pthread_mutex_lock (scm_i_pthread_mutex_t *mutex)
|
||||
{
|
||||
scm_i_scm_pthread_mutex_lock (mutex);
|
||||
scm_frame_unwind_handler (unlock, mutex, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_unwind_handler (unlock, mutex, SCM_F_WIND_EXPLICITLY);
|
||||
}
|
||||
|
||||
int
|
||||
|
@ -1579,15 +1579,15 @@ scm_i_thread_sleep_for_gc ()
|
|||
scm_i_pthread_mutex_t scm_i_critical_section_mutex;
|
||||
int scm_i_critical_section_level = 0;
|
||||
|
||||
static SCM framed_critical_section_mutex;
|
||||
static SCM dynwind_critical_section_mutex;
|
||||
|
||||
void
|
||||
scm_frame_critical_section (SCM mutex)
|
||||
scm_dynwind_critical_section (SCM mutex)
|
||||
{
|
||||
if (scm_is_false (mutex))
|
||||
mutex = framed_critical_section_mutex;
|
||||
scm_frame_lock_mutex (mutex);
|
||||
scm_frame_block_asyncs ();
|
||||
mutex = dynwind_critical_section_mutex;
|
||||
scm_dynwind_lock_mutex (mutex);
|
||||
scm_dynwind_block_asyncs ();
|
||||
}
|
||||
|
||||
/*** Initialization */
|
||||
|
@ -1645,7 +1645,7 @@ scm_init_threads ()
|
|||
guilify_self_2 (SCM_BOOL_F);
|
||||
threads_initialized_p = 1;
|
||||
|
||||
framed_critical_section_mutex =
|
||||
dynwind_critical_section_mutex =
|
||||
scm_permanent_object (scm_make_recursive_mutex ());
|
||||
}
|
||||
|
||||
|
|
|
@ -158,7 +158,7 @@ SCM_API SCM scm_join_thread (SCM t);
|
|||
SCM_API SCM scm_make_mutex (void);
|
||||
SCM_API SCM scm_make_recursive_mutex (void);
|
||||
SCM_API SCM scm_lock_mutex (SCM m);
|
||||
SCM_API void scm_frame_lock_mutex (SCM mutex);
|
||||
SCM_API void scm_dynwind_lock_mutex (SCM mutex);
|
||||
SCM_API SCM scm_try_mutex (SCM m);
|
||||
SCM_API SCM scm_unlock_mutex (SCM m);
|
||||
|
||||
|
@ -175,7 +175,7 @@ SCM_API SCM scm_all_threads (void);
|
|||
SCM_API int scm_c_thread_exited_p (SCM thread);
|
||||
SCM_API SCM scm_thread_exited_p (SCM thread);
|
||||
|
||||
SCM_API void scm_frame_critical_section (SCM mutex);
|
||||
SCM_API void scm_dynwind_critical_section (SCM mutex);
|
||||
|
||||
#define SCM_I_CURRENT_THREAD \
|
||||
((scm_i_thread *) scm_i_pthread_getspecific (scm_i_thread_key))
|
||||
|
@ -195,7 +195,7 @@ SCM_API scm_i_pthread_mutex_t scm_i_misc_mutex;
|
|||
|
||||
#if SCM_USE_PTHREAD_THREADS
|
||||
SCM_API int scm_pthread_mutex_lock (pthread_mutex_t *mutex);
|
||||
SCM_API void scm_frame_pthread_mutex_lock (pthread_mutex_t *mutex);
|
||||
SCM_API void scm_dynwind_pthread_mutex_lock (pthread_mutex_t *mutex);
|
||||
SCM_API int scm_pthread_cond_wait (pthread_cond_t *cond,
|
||||
pthread_mutex_t *mutex);
|
||||
SCM_API int scm_pthread_cond_timedwait (pthread_cond_t *cond,
|
||||
|
|
|
@ -33,10 +33,10 @@ set_flag (void *data)
|
|||
void
|
||||
func1 ()
|
||||
{
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
flag1 = 0;
|
||||
scm_frame_unwind_handler (set_flag, &flag1, 0);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_unwind_handler (set_flag, &flag1, 0);
|
||||
scm_dynwind_end ();
|
||||
}
|
||||
|
||||
/* FUNC2 should set flag1.
|
||||
|
@ -45,10 +45,10 @@ func1 ()
|
|||
void
|
||||
func2 ()
|
||||
{
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
flag1 = 0;
|
||||
scm_frame_unwind_handler (set_flag, &flag1, SCM_F_WIND_EXPLICITLY);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_unwind_handler (set_flag, &flag1, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_end ();
|
||||
}
|
||||
|
||||
/* FUNC3 should set flag1.
|
||||
|
@ -57,11 +57,11 @@ func2 ()
|
|||
void
|
||||
func3 ()
|
||||
{
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
flag1 = 0;
|
||||
scm_frame_unwind_handler (set_flag, &flag1, 0);
|
||||
scm_dynwind_unwind_handler (set_flag, &flag1, 0);
|
||||
scm_misc_error ("func3", "gratuitous error", SCM_EOL);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
}
|
||||
|
||||
/* FUNC4 should set flag1.
|
||||
|
@ -70,11 +70,11 @@ func3 ()
|
|||
void
|
||||
func4 ()
|
||||
{
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
flag1 = 0;
|
||||
scm_frame_unwind_handler (set_flag, &flag1, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_unwind_handler (set_flag, &flag1, SCM_F_WIND_EXPLICITLY);
|
||||
scm_misc_error ("func4", "gratuitous error", SCM_EOL);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
}
|
||||
|
||||
SCM
|
||||
|
@ -107,14 +107,14 @@ check_flag1 (const char *tag, void (*func)(void), int val)
|
|||
SCM
|
||||
check_cont_body (void *data)
|
||||
{
|
||||
scm_t_frame_flags flags = (data? SCM_F_FRAME_REWINDABLE : 0);
|
||||
scm_t_dynwind_flags flags = (data? SCM_F_DYNWIND_REWINDABLE : 0);
|
||||
int first;
|
||||
SCM val;
|
||||
|
||||
scm_frame_begin (flags);
|
||||
scm_dynwind_begin (flags);
|
||||
|
||||
val = scm_make_continuation (&first);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
return val;
|
||||
}
|
||||
|
||||
|
@ -138,7 +138,7 @@ check_cont (int rewindable)
|
|||
}
|
||||
else if (scm_is_false (res))
|
||||
{
|
||||
/* the result of invoking the continuation, frame must be
|
||||
/* the result of invoking the continuation, dynwind must be
|
||||
rewindable */
|
||||
if (rewindable)
|
||||
return;
|
||||
|
@ -147,7 +147,7 @@ check_cont (int rewindable)
|
|||
}
|
||||
else
|
||||
{
|
||||
/* the catch tag, frame must not have been rewindable. */
|
||||
/* the catch tag, dynwind must not have been rewindable. */
|
||||
if (!rewindable)
|
||||
return;
|
||||
printf ("continuation didn't work\n");
|
||||
|
@ -175,28 +175,28 @@ check_ports ()
|
|||
if (mktemp (filename) == NULL)
|
||||
exit (1);
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
{
|
||||
SCM port = scm_open_file (scm_from_locale_string (filename),
|
||||
scm_from_locale_string ("w"));
|
||||
scm_frame_unwind_handler_with_scm (close_port, port,
|
||||
scm_dynwind_unwind_handler_with_scm (close_port, port,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
|
||||
scm_frame_current_output_port (port);
|
||||
scm_dynwind_current_output_port (port);
|
||||
scm_write (scm_version (), SCM_UNDEFINED);
|
||||
}
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_dynwind_begin (0);
|
||||
{
|
||||
SCM port = scm_open_file (scm_from_locale_string (filename),
|
||||
scm_from_locale_string ("r"));
|
||||
SCM res;
|
||||
scm_frame_unwind_handler_with_scm (close_port, port,
|
||||
scm_dynwind_unwind_handler_with_scm (close_port, port,
|
||||
SCM_F_WIND_EXPLICITLY);
|
||||
scm_frame_unwind_handler (delete_file, filename, SCM_F_WIND_EXPLICITLY);
|
||||
scm_dynwind_unwind_handler (delete_file, filename, SCM_F_WIND_EXPLICITLY);
|
||||
|
||||
scm_frame_current_input_port (port);
|
||||
scm_dynwind_current_input_port (port);
|
||||
res = scm_read (SCM_UNDEFINED);
|
||||
if (scm_is_false (scm_equal_p (res, scm_version ())))
|
||||
{
|
||||
|
@ -204,7 +204,7 @@ check_ports ()
|
|||
exit (1);
|
||||
}
|
||||
}
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -215,10 +215,10 @@ check_fluid ()
|
|||
|
||||
scm_fluid_set_x (f, scm_from_int (12));
|
||||
|
||||
scm_frame_begin (0);
|
||||
scm_frame_fluid (f, scm_from_int (13));
|
||||
scm_dynwind_begin (0);
|
||||
scm_dynwind_fluid (f, scm_from_int (13));
|
||||
x = scm_fluid_ref (f);
|
||||
scm_frame_end ();
|
||||
scm_dynwind_end ();
|
||||
|
||||
if (!scm_is_eq (x, scm_from_int (13)))
|
||||
{
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue