From: Alexey Dejneka Date: Mon, 17 Nov 2003 15:41:26 +0000 (+0000) Subject: 0.8.5.45: X-Git-Url: http://repo.macrolet.net/gitweb/?a=commitdiff_plain;h=178c287e841e5278c17b762a480a74d29f024b20;p=sbcl.git 0.8.5.45: * Describe modular arithmetic optimization. --- diff --git a/BUGS b/BUGS index c74909d..0101f27 100644 --- a/BUGS +++ b/BUGS @@ -1201,3 +1201,15 @@ WORKAROUND: (0))). However, an integral value of X should be legal, because successive adds of integers to double-floats produces double-floats, so none of the type restrictions in the code is violated. + +298: (aka PFD MISC.183) + Compiler fails on + + (defun foo () + (multiple-value-call #'bar + (ext) + (catch 'tag (return-from foo (int))))) + + This program violates "unknown values LVAR stack discipline": if INT + returns, values returned by (EXT) must be removed from under that of + (INT). diff --git a/doc/efficiency.sgml b/doc/efficiency.sgml index 2f5516b..10d5761 100644 --- a/doc/efficiency.sgml +++ b/doc/efficiency.sgml @@ -87,4 +87,46 @@ sources. Such code is often reasonably straightforward to write; search the sources for the string deftransform to find many examples (some straightforward, some less so). +Modular arithmetic</> +<para> +Some numeric functions have a property: <varname>N</> lower bits of +the result depend only on <varname>N</> lower bits of (all or some) +arguments. If the compiler sees an expression of form <literal>(logand +exp mask)</>, where <varname>exp</> is a tree of such "good" functions +and <varname>mask</> is known to be of type <type>(unsigned-byte +w)</>, where <varname>w</> is a "good" width, all intermediate results +will be cut to <varname>w</> bits (but it is not done for variables +and constants!). This often results in an ability to use simple +machine instructions for the functions. +</para> + +<para> +Consider an example. +<programlisting> +(defun i (x y) + (declare (type (unsigned-byte 32) x y)) + (ldb (byte 32 0) (logxor x (lognot y)))) +</programlisting> +The result of <literal>(lognot y)</> will be negative and of +type <type>(signed-byte 33)</>, so a naive implementation on a 32-bit +platform is unable to use 32-bit arithmetic here. But modular +arithmetic optimizer is able to do it: because the result is cut down +to 32 bits, the compiler will replace <function>logxor</> +and <function>lognot</> with versions cutting results to 32 bits, and +because terminals (here---expressions <literal>x</> and <literal>y</>) +are also of type <type>(unsigned-byte 32)</>, 32-bit machine +arithmetic can be used. +</para> + +<note><para> As of &SBCL; 0.8.5 "good" functions +are <function>+</>, <function>-</>; <function>logand</>, <function>logior</>, +<function>logxor</>, <function>lognot</> and their combinations; +and <function>ash</> with the positive second argument. "Good" widths +are 32 on HPPA, MIPS, PPC, Sparc and X86 and 64 on Alpha. While it is +possible to support smaller widths as well, currently it is not +implemented. +</para></note> + +</sect1> + </chapter> diff --git a/version.lisp-expr b/version.lisp-expr index 652311a..94e8515 100644 --- a/version.lisp-expr +++ b/version.lisp-expr @@ -17,4 +17,4 @@ ;;; checkins which aren't released. (And occasionally for internal ;;; versions, especially for internal versions off the main CVS ;;; branch, it gets hairier, e.g. "0.pre7.14.flaky4.13".) -"0.8.5.45" +"0.8.5.46"