From: Taylor R Campbell Date: Sat, 24 Aug 2019 07:07:11 +0000 (+0000) Subject: Update and clarify fp-env documentation. X-Git-Tag: mit-scheme-pucked-10.1.20~11^2~70 X-Git-Url: https://birchwood-abbey.net/git?a=commitdiff_plain;h=ba48a1bef22c24a00aec7fd9b5a506a2f88cbf8e;p=mit-scheme.git Update and clarify fp-env documentation. --- diff --git a/doc/ref-manual/numbers.texi b/doc/ref-manual/numbers.texi index 5c81be967..99a788f46 100644 --- a/doc/ref-manual/numbers.texi +++ b/doc/ref-manual/numbers.texi @@ -2430,26 +2430,52 @@ If @var{quiet?} is false, @var{payload} must be nonzero. @node Floating-Point Environment, Floating-Point Exceptions, Flonum Operations, Fixnum and Flonum Operations @subsection Floating-Point Environment +@cindex floating-point environment The @acronym{IEEE 754-2008} computation model includes a persistent -rounding mode and exception flags. -In MIT/GNU Scheme, every thread has its own floating-point -environment, initialized to the default @acronym{IEEE 754-2008} -environment, with no exceptions trapped, with no exceptions raised, -and with round-to-nearest/ties-to-even. +rounding mode, exception flags, and exception-handling modes. +In MIT/GNU Scheme, the floating-point environment is per-thread. +However, because saving and restoring the floating-point environment +is expensive, it is maintained only for those threads that have +touched the floating-point environment explicitly, either: + +@itemize @bullet +@item +during a procedure such as @code{flo:with-exceptions-trapped} that +establishes a change to the floating-point environment for a dynamic +extent, or + +@item +after @code{flo:set-environment!} to a non-default environment (but +not after @code{flo:set-environment!} to the default environment), or + +@item +after various other procedures such as @code{flo:clear-exceptions!} +that explicitly change the floating-point environment. +@end itemize + +@noindent +@cindex floating-point environment, default +@cindex default environment, floating-point +The default environment is as in @acronym{IEEE 754-2008}: no +exceptions are trapped, and rounding is to nearest with ties broken to +even. +The set of exception flags in the default environment is indeterminate +--- callers must enter a per-thread environment, e.g. by calling +@code{flo:clear-exceptions!}, before acting on the exception flags. +Like the default environment, a per-thread environment initially has +no exceptions trapped and rounds to nearest with ties to even. -@cindex floating-point environment A @strong{floating-point environment} descriptor is a machine-dependent object representing the @acronym{IEEE 754-2008} -floating-point exception flags, exception-handling mode (trap or no -trap), and rounding mode. +floating-point rounding mode, exception flags, and exception-handling +mode. Users should not inspect a floating-point environment descriptor other than to use it with the procedures here; its representation may vary from system to system. @deffn procedure flo:default-environment -Returns a descriptor for the default floating-point environment, with -no exceptions trapped, no exceptions raised, and -round-to-nearest/ties-to-even. +Returns a descriptor for the default environment, with no exceptions +trapped and round-to-nearest/ties-to-even. @end deffn @deffn procedure flo:environment @@ -2469,30 +2495,41 @@ exceptions in a large intermediate computation until the end. @end deffn @deffn procedure flo:preserving-environment thunk -Saves the current floating-point environment and calls @var{thunk}. +Saves the current floating-point environment if any and calls +@var{thunk}. On exit from @var{thunk}, including non-local exit, saves @var{thunk}'s floating-point environment and restores the original floating-point environment as if with @code{flo:set-environment!}. On re-entry into @var{thunk}, restores @var{thunk}'s floating-point environment. + +@strong{Note:} @code{Flo:preserving-environment} @emph{does not} enter +a per-thread environment. +If the current thread is in the default environment, the exception +flags are indeterminate, and remain so inside +@code{flo:preserving-environment}. +Callers interested in using the exception flags should start inside +@code{flo:preserving-environment} by clearing them with +@code{flo:clear-exceptions!}. @end deffn @node Floating-Point Exceptions, Floating-Point Rounding Mode, Floating-Point Environment, Fixnum and Flonum Operations @subsection Floating-Point Exceptions -Floating-point computations such as arithmetic may raise exceptions. +In @acronym{IEEE 754-2008}, floating-point operations such as +arithmetic may raise exceptions. This sets a flag in the floating-point environment that is maintained -until it is cleared, and, if the exception is trapped, signals a -Scheme condition. -Most machines support trapping exceptions, but not all --- for -example, most ARM CPUs do not. -In the default floating-point environment, no exceptions are trapped -and no exceptions are raised. +until it is cleared. +Many machines can also be configured to trap on exceptions, which in +Scheme leads to signalling a condition. +(Not all CPUs support trapping exceptions --- for example, most ARMv8 +CPUs do not.) +In the default environment, no exceptions are trapped. Floating-point exceptions and sets of floating-point exceptions are represented by small integers, whose interpretation is -machine-dependent --- for example, the invalid-operation exception may -be represented differently on PowerPC and AMD x86-64 CPUs. +machine-dependent --- for example, the invalid-operation exception +may be represented differently on PowerPC and AMD x86-64 CPUs. The number for a floating-point exception is the same as the number for a set of exceptions containing only that one; the bitwise-AND of two sets is their intersection, the bitwise-IOR is their union, etc. @@ -2509,7 +2546,7 @@ The following exceptions are recognized by MIT/GNU Scheme: Raised when the result of a floating-point computation is not a floating-point number and therefore must be rounded. -The inexact-result exception is never trappable. +The inexact-result exception is never trappable in MIT/GNU Scheme. @item underflow @cindex underflow exception @@ -2526,7 +2563,8 @@ therefore rounded to infinity. @item divide-by-zero @cindex divide-by-zero exception Raised on division of a nonzero finite real number by a zero real -number, or logarithm of zero. +number, or logarithm of zero, or other operation that has an unbounded +limit at a point like division by a divisor approaching zero. @item invalid-operation @cindex invalid-operation exception @@ -2583,11 +2621,15 @@ of exceptions by a list of human-readable symbols naming them. @deffn procedure flo:test-exceptions excepts Returns the set of exceptions in @var{excepts} that are currently raised. + +In the default environment, the result is indeterminate, and may +be affected by floating-point operations in other threads. @end deffn @deffn procedure flo:clear-exceptions! excepts @deffnx procedure flo:raise-exceptions! excepts -Clears and raises the exceptions in @var{excepts}. +Clears or raises the exceptions in @var{excepts}, entering a +per-thread environment. Other exceptions are unaffected. @end deffn @@ -2596,7 +2638,8 @@ Other exceptions are unaffected. @deffnx procedure flo:test-exception-flags exceptflags excepts @code{Flo:save-exception-flags} returns a machine-dependent representation of the currently trapped and raised exceptions. -@code{Flo:restore-exception-flags!} restores it. +@code{Flo:restore-exception-flags!} restores it, entering a per-thread +environment. @code{Flo:test-exception-flags} returns the set of exceptions in @var{excepts} that are raised in @var{exceptflags}. @@ -2634,6 +2677,7 @@ currently trapped. @var{excepts} not be trapped. @code{Flo:set-trapped-exceptions!} replaces the set of trapped exceptions altogether by @var{excepts}. +All three procedures enter a per-thread environment. @example @group @@ -2659,7 +2703,8 @@ exceptions altogether by @var{excepts}. Dynamic-extent analogues of @code{flo:trap-exceptions!}, @code{flo:untrap-exceptions!}, and @code{flo:set-trapped-exceptions!}. These call @var{thunk} with their respective changes to the set of -trapped exceptions, and restore it on return or non-local exit. +trapped exceptions in a per-thread environment, and restore the +environment on return or non-local exit. @end deffn @deffn procedure flo:defer-exception-traps! @@ -2667,9 +2712,9 @@ Saves the current floating-point environment, clears all raised exceptions, disables all exception traps, and returns a descriptor for the saved floating-point environment. -This is typically used together with @code{flo:update-environment!}, -to trap any exceptions that the caller had wanted trapped only after a -long intermediate computation. +@code{Flo:defer-exception-traps!} is typically used together with +@code{flo:update-environment!}, to trap any exceptions that the caller +had wanted trapped only after a long intermediate computation. This pattern is captured in @code{flo:deferring-exception-traps}. @end deffn @@ -2750,12 +2795,15 @@ Returns a list of the supported rounding modes as symbols. @deffn procedure flo:rounding-mode @deffnx procedure flo:set-rounding-mode! mode -Gets or sets the current rounding mode as a symbol. +Gets or sets the current rounding mode as a symbol, entering a +per-thread environment. @end deffn @deffn procedure flo:with-rounding-mode mode thunk -Call @var{thunk} with the rounding mode set to @var{mode}. -On return, the rounding mode is restored to what it was before. +Call @var{thunk} in a per-thread environment with the rounding mode +set to @var{mode}. +On return, the floating-point environment, including rounding mode, is +restored to what it was before. Non-local exit from and re-entrance to @var{thunk} behaves as if the call is surrounded by @code{flo:preserving-environment}