0.8.9.13
[sbcl.git] / doc / manual / efficiency.texinfo
1 @node Efficiency, Beyond The ANSI Standard, The Debugger, Top
2 @comment  node-name,  next,  previous,  up
3 @chapter Efficiency
4
5 FIXME: The material in the CMUCL manual about getting good
6 performance from the compiler should be reviewed, reformatted in
7 Texinfo, lightly edited for SBCL, and substituted into this
8 manual. In the meantime, the original CMUCL manual is still 95+%
9 correct for the SBCL version of the Python compiler. See the
10 sections
11
12 @itemize
13 @item Advanced Compiler Use and Efficiency Hints
14 @item Advanced Compiler Introduction
15 @item More About Types in Python
16 @item Type Inference
17 @item Source Optimization
18 @item Tail Recursion
19 @item Local Call
20 @item Block Compilation
21 @item Inline Expansion
22 @item Object Representation
23 @item Numbers
24 @item General Efficiency Hints
25 @item Efficiency Notes
26 @end itemize
27
28 Besides this information from the CMUCL manual, there are a few other
29 points to keep in mind.
30
31 @itemize
32   
33 @item
34 The CMUCL manual doesn't seem to state it explicitly, but Python has a
35 mental block about type inference when assignment is involved. Python
36 is very aggressive and clever about inferring the types of values
37 bound with @code{let}, @code{let*}, inline function call, and so
38 forth. However, it's much more passive and dumb about inferring the
39 types of values assigned with @code{setq}, @code{setf}, and
40 friends. It would be nice to fix this, but in the meantime don't
41 expect that just because it's very smart about types in most respects
42 it will be smart about types involved in assignments.  (This doesn't
43 affect its ability to benefit from explicit type declarations
44 involving the assigned variables, only its ability to get by without
45 explicit type declarations.)
46
47 @c <!-- FIXME: Python dislikes assignments, but not in type
48 @c     inference. The real problems are loop induction, closed over
49 @c     variables and aliases. -->
50   
51 @item
52 Since the time the CMUCL manual was written, CMUCL (and thus SBCL) has
53 gotten a generational garbage collector. This means that there are
54 some efficiency implications of various patterns of memory usage which
55 aren't discussed in the CMUCL manual. (Some new material should be
56 written about this.)
57   
58 @item
59 SBCL has some important known efficiency problems.  Perhaps the most
60 important are
61     
62 @itemize @minus
63       
64 @item
65 There is no support for the ANSI @code{dynamic-extent} declaration,
66 not even for closures or @code{&rest} lists.
67       
68 @item
69 The garbage collector is not particularly efficient, at least on
70 platforms without the generational collector (as of SBCL 0.8.9, all
71 except x86).
72       
73 @item
74 Various aspects of the PCL implementation of CLOS are more inefficient
75 than necessary.
76     
77 @end itemize
78
79 @end itemize
80
81 Finally, note that Common Lisp defines many constructs which, in
82 the infamous phrase, ``could be compiled efficiently by a
83 sufficiently smart compiler''. The phrase is infamous because
84 making a compiler which actually is sufficiently smart to find all
85 these optimizations systematically is well beyond the state of the art
86 of current compiler technology. Instead, they're optimized on a
87 case-by-case basis by hand-written code, or not optimized at all if
88 the appropriate case hasn't been hand-coded. Some cases where no such
89 hand-coding has been done as of SBCL version 0.6.3 include
90
91 @itemize
92   
93 @item
94 @code{(reduce #'f x)} where the type of @code{x} is known at compile
95 time
96   
97 @item
98 various bit vector operations, e.g.  @code{(position 0
99 some-bit-vector)}
100
101 @end itemize
102
103 If your system's performance is suffering because of some construct
104 which could in principle be compiled efficiently, but which the SBCL
105 compiler can't in practice compile efficiently, consider writing a
106 patch to the compiler and submitting it for inclusion in the main
107 sources. Such code is often reasonably straightforward to write;
108 search the sources for the string ``@code{deftransform}'' to find many
109 examples (some straightforward, some less so).
110
111 @menu
112 * Modular arithmetic::          
113 @end menu
114
115 @node  Modular arithmetic,  , Efficiency, Efficiency
116 @comment  node-name,  next,  previous,  up
117 @section Modular arithmetic
118
119 Some numeric functions have a property: @var{N} lower bits of the
120 result depend only on @var{N} lower bits of (all or some)
121 arguments. If the compiler sees an expression of form @code{(logand
122 @var{exp} @var{mask})}, where @var{exp} is a tree of such ``good''
123 functions and @var{mask} is known to be of type @code{(unsigned-byte
124 @var{w})}, where @var{w} is a ``good'' width, all intermediate results
125 will be cut to @var{w} bits (but it is not done for variables and
126 constants!). This often results in an ability to use simple machine
127 instructions for the functions.
128
129 Consider an example.
130
131 @lisp
132 (defun i (x y)
133   (declare (type (unsigned-byte 32) x y))
134   (ldb (byte 32 0) (logxor x (lognot y))))
135 @end lisp
136
137 The result of @code{(lognot y)} will be negative and of type
138 @code{(signed-byte 33)}, so a naive implementation on a 32-bit
139 platform is unable to use 32-bit arithmetic here. But modular
140 arithmetic optimizer is able to do it: because the result is cut down
141 to 32 bits, the compiler will replace @code{logxor} and @code{lognot}
142 with versions cutting results to 32 bits, and because terminals
143 (here---expressions @code{x} and @code{y}) are also of type
144 @code{(unsigned-byte 32)}, 32-bit machine arithmetic can be used.
145
146
147 As of SBCL 0.8.5 ``good'' functions are @code{+}, @code{-};
148 @code{logand}, @code{logior}, @code{logxor}, @code{lognot} and their
149 combinations; and @code{ash} with the positive second
150 argument. ``Good'' widths are 32 on HPPA, MIPS, PPC, Sparc and X86 and
151 64 on Alpha. While it is possible to support smaller widths as well,
152 currently it is not implemented.