@node Data and control flow
@section Data and control flow

@node Shadowed bindings
@cindex Shadowed bindings in LET, FLET, LABELS and lambda-list
@subsection Shadowed bindings
ANSI doesn't specify what should happen if any of the @code{LET},
@code{FLET} and @code{LABELS} special operators contain many bindings
sharing the same name. Because the behavior varies between the
implementations and the programmer can't rely on the spec ECL signals an
error if such situation occur.

Moreover, while ANSI defines lambda list parameters in the terms of
@code{LET*}, when used in function context programmer can't provide an
initialization forms for required parameters. If required parameters
share the same name the error is signalled.

Described behavior is present in ECL since version 16.0.0. Previously
the @code{LET} operator were using first binding. Both @code{FLET} and
@code{LABELS} were signalling an error if C compiler was used and used
the last binding as a visible one when the byte compiler was used.

@node Minimal compilation
@cindex Bytecodes eager compilation
@lspindex si::make-lambda
@subsection Minimal compilation
Former versions of ECL, as well as many other lisps, used linked lists
to represent code. Executing code thus meant traversing these lists and
performing code transformations, such as macro expansion, every time
that a statement was to be executed. The result was a slow and memory
hungry interpreter.

Beginning with version 0.3, ECL was shipped with a bytecodes compiler
and interpreter which circumvent the limitations of linked lists. When
you enter code at the lisp prompt, or when you load a source file, ECL
begins a process known as minimal compilation. Barely this process
consists on parsing each form, macroexpanding it and translating it into
an intermediate language made of bytecodes.

The bytecodes compiler is implemented in src/c/compiler.d. The main
entry point is the lisp function si::make-lambda, which takes a name for
the function and the body of the lambda lists, and produces a lisp
object that can be invoked. For instance,

@exindex @code{si::make-lambda} usage (bytecodes compilation)
@lisp
> (defvar fun (si::make-lambda 'f '((x) (1+ x))))
*FUN*
> (funcall fun 2)
3
@end lisp

ECL can only execute bytecodes. When a list is passed to EVAL it must be
first compiled to bytecodes and, if the process succeeds, the resulting
bytecodes are passed to the interpreter. Similarly, every time a
function object is created, such as in DEFUN or DEFMACRO, the compiler
processes the lambda form to produce a suitable bytecodes object.

@cindex Eager compilation implications

The fact that ECL performs this eager compilation means that changes on
a macro are not immediately seen in code which was already
compiled. This has subtle implications. Take the following code:

@exindex Eager compilation impact on macros
@lisp
> (defmacro f (a b) `(+ ,a ,b))
F
> (defun g (x y) (f x y))
G
> (g 1 2)
3
> (defmacro f (a b) `(- ,a ,b))
F
> (g 1 2)
3
@end lisp

The last statement always outputs 3 while in former implementations
based on simple list traversal it would produce -1.

@node Function types
@subsection Function types

Functions in ECL can be of two types: they are either compiled to
bytecodes or they have been compiled to machine code using a lisp to C
translator and a C compiler. To the first category belong function
loaded from lisp source files or entered at the toplevel. To the second
category belong all functions in the ECL core environment and functions
in files processed by compile or compile-file.

The output of (symbol-function fun) is one of the following:
@itemize
@item a function object denoting the definition of the function fun,
@item a list of the form (macro . function-object) when fun denotes a macro,
@item or simply 'special, when fun denotes a special form, such as block, if, etc.
@end itemize

@cindex @code{disassemble} and @code{compile} on defined functions
@exindex Keeping lambda definitions with @code{si:*keep-definitions}

ECL usually drops the source code of a function unless the global
variable si:*keep-definitions* was true when the function was translated
into bytecodes. Therefore, if you wish to use compile and disassemble on
defined functions, you should issue @code{(setq si:*keep-definitions*
t)} at the beginning of your session.

@lspindex si:*keep-definitions*
@defvr {SI} {*keep-definitions*}
If set to @code{T} ECL will preserve the compiled function source code
for disassembly and recompilation.
@end defvr

@cindex Common Lisp functions limits
@lspindex call-arguments-limit
@lspindex lambda-parameters-limit
@lspindex multiple-values-limit
@lspindex lambda-list-keywords

In @ref{tab:fun-const} we list all Common Lisp values related to the limits of functions.
@float Table,tab:fun-const
@caption{Function related constants}
@multitable @columnfractions 0.3 0.7
@item call-arguments-limit
@tab 65536

@item lambda-parameters-limit
@tab @code{call-arguments-limit}

@item multiple-values-limit
@tab 64

@item lambda-list-keywords
@tab @code{(&optional &rest &key &allow-other-keys &aux &whole &environment &body)}
@end multitable
@end float

