mirror of
git://git.code.sf.net/p/sbcl/sbcl
synced 2026-09-10 07:26:40 -04:00
doc: update generated texinfo files
This commit is contained in:
parent
316291e371
commit
b3bfe02876
|
|
@ -1,39 +1,68 @@
|
|||
@node sb-aclrepl
|
||||
@section sb-aclrepl
|
||||
@cindex Read-Eval-Print Loop
|
||||
@cindex REPL
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node sb aclrepl
|
||||
@section sb-aclrepl
|
||||
|
||||
@menu
|
||||
* Usage: sb aclrepl usage.
|
||||
* Customization: sb aclrepl customization.
|
||||
* Example Initialization: sb aclrepl example initialization.
|
||||
@end menu
|
||||
|
||||
@c FIXME: I wanted to use @registeredsymbol{}, but that's
|
||||
@c only available in Texinfo 4.7. sigh.
|
||||
The @code{sb-aclrepl} module offers an Allegro CL-style
|
||||
Read-Eval-Print Loop for SBCL, with integrated inspector. Adding a
|
||||
debugger interface is planned.
|
||||
|
||||
Allegro CL is a registered trademark of Franz Inc.
|
||||
|
||||
@node sb aclrepl usage
|
||||
@subsection Usage
|
||||
|
||||
To start @code{sb-aclrepl} as your read-eval-print loop, put the form
|
||||
@lisp
|
||||
|
||||
@example
|
||||
(require 'sb-aclrepl)
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
in your @file{~/.sbclrc} initialization file.
|
||||
in your @code{~/.sbclrc}, one of your @ref{initialization files}.
|
||||
|
||||
@node sb aclrepl customization
|
||||
@subsection Customization
|
||||
|
||||
The following customization variables are available:
|
||||
|
||||
@include var-sb-aclrepl-star-command-char-star.texinfo
|
||||
@include var-sb-aclrepl-star-prompt-star.texinfo
|
||||
@include var-sb-aclrepl-star-exit-on-eof-star.texinfo
|
||||
@include var-sb-aclrepl-star-use-short-package-name-star.texinfo
|
||||
@include var-sb-aclrepl-star-max-history-star.texinfo
|
||||
|
||||
@anchor{Variable sb-aclrepl *command-char*}
|
||||
@vvindex @sortas{command-char* sb-aclrepl} *command-char* [sb-aclrepl]
|
||||
@deffn{Variable} sb-aclrepl:*command-char*
|
||||
Prefix character for a top-level command
|
||||
@end deffn
|
||||
@anchor{Variable sb-aclrepl *prompt*}
|
||||
@vvindex @sortas{prompt* sb-aclrepl} *prompt* [sb-aclrepl]
|
||||
@deffn{Variable} sb-aclrepl:*prompt*
|
||||
The current prompt string or formatter function.
|
||||
@end deffn
|
||||
@anchor{Variable sb-aclrepl *exit-on-eof*}
|
||||
@vvindex @sortas{exit-on-eof* sb-aclrepl} *exit-on-eof* [sb-aclrepl]
|
||||
@deffn{Variable} sb-aclrepl:*exit-on-eof*
|
||||
If @code{t}, then exit when the EOF character is entered.
|
||||
@end deffn
|
||||
@anchor{Variable sb-aclrepl *use-short-package-name*}
|
||||
@vvindex @sortas{use-short-package-name* sb-aclrepl} *use-short-package-name* [sb-aclrepl]
|
||||
@deffn{Variable} sb-aclrepl:*use-short-package-name*
|
||||
When @code{t}, use the shortnest package nickname in a prompt
|
||||
@end deffn
|
||||
@anchor{Variable sb-aclrepl *max-history*}
|
||||
@vvindex @sortas{max-history* sb-aclrepl} *max-history* [sb-aclrepl]
|
||||
@deffn{Variable} sb-aclrepl:*max-history*
|
||||
Maximum number of history commands to remember
|
||||
@end deffn
|
||||
@node sb aclrepl example initialization
|
||||
@subsection Example Initialization
|
||||
|
||||
Here's a longer example of a @file{~/.sbclrc} file that shows off
|
||||
some of the features of @code{sb-aclrepl}:
|
||||
Here's a longer example of a @code{~/.sbclrc} file that shows off
|
||||
some of the features of sb-aclrepl:
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(ignore-errors (require 'sb-aclrepl))
|
||||
|
||||
(when (find-package 'sb-aclrepl)
|
||||
|
|
@ -51,11 +80,8 @@ some of the features of @code{sb-aclrepl}:
|
|||
;; such as ":r base64"
|
||||
(sb-aclrepl:alias ("require" 0 "Require module") (sys) (require sys))
|
||||
(setq cl:*features* (delete :aclrepl cl:*features*)))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
Questions, comments, or bug reports should be sent to Kevin Rosenberg
|
||||
(@email{kevin@@rosenberg.net}).
|
||||
(kevin@@rosenberg.net).
|
||||
|
||||
@subsection Credits
|
||||
|
||||
Allegro CL is a registered trademark of Franz Inc.
|
||||
|
|
|
|||
|
|
@ -1,192 +1,368 @@
|
|||
@node Networking
|
||||
@comment node-name, next, previous, up
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node networking
|
||||
@chapter Networking
|
||||
@cindex Sockets, Networking
|
||||
|
||||
@menu
|
||||
* Sockets Overview: sockets overview.
|
||||
* General Sockets: general sockets.
|
||||
* Socket Options: socket options.
|
||||
* INET Domain Sockets: inet domain sockets.
|
||||
* Local Domain Sockets: local domain sockets.
|
||||
* Name Service: name service.
|
||||
@end menu
|
||||
|
||||
The @code{sb-bsd-sockets} module provides a thinly disguised BSD
|
||||
socket API for SBCL. Ideas have been stolen from the BSD socket API
|
||||
for C and Graham Barr's IO::Socket classes for Perl.
|
||||
for C and Graham Barr's @code{IO::Socket} classes for Perl.
|
||||
|
||||
Sockets are represented as CLOS objects, and the API naming
|
||||
conventions attempt to balance between the BSD names and good lisp style.
|
||||
conventions attempt to balance between the BSD names and good lisp
|
||||
style.
|
||||
|
||||
@menu
|
||||
* Sockets Overview::
|
||||
* General Sockets:: Methods applicable to all sockets
|
||||
* Socket Options::
|
||||
* INET Domain Sockets::
|
||||
* Local (Unix) Domain Sockets::
|
||||
* Name Service::
|
||||
@end menu
|
||||
|
||||
@node Sockets Overview
|
||||
@node sockets overview
|
||||
@section Sockets Overview
|
||||
|
||||
Most of the functions are modelled on the BSD socket API. BSD sockets
|
||||
are widely supported, portably @emph{(``portable'' by Unix standards, at least)}
|
||||
are widely supported, portably (by Unix standards, at least)
|
||||
available on a variety of systems, and documented. There are some
|
||||
differences in approach where we have taken advantage of some of the
|
||||
more useful features of Common Lisp - briefly:
|
||||
more useful features of Common Lisp -- briefly:
|
||||
|
||||
@itemize
|
||||
@item Where the C API would typically return -1 and set @code{errno},
|
||||
@code{sb-bsd-sockets} signals an error. All the errors are subclasses
|
||||
of @code{sb-bsd-sockets:socket-error} and generally correspond one for
|
||||
one with possible @code{errno} values.
|
||||
|
||||
@item
|
||||
Where the C API would typically return -1 and set @code{errno},
|
||||
@code{sb-bsd-sockets} signals an error. All the errors are subclasses
|
||||
of @code{sb-bsd-sockets:socket-condition} and generally correspond one
|
||||
for one with possible @code{errno} values.
|
||||
@item We use multiple return values in many places where the C API would
|
||||
use pass-by-reference values.
|
||||
|
||||
@item
|
||||
We use multiple return values in many places where the C API would use
|
||||
pass-by-reference values.
|
||||
|
||||
@item
|
||||
We can often avoid supplying an explicit @emph{length} argument to
|
||||
functions because we already know how long the argument is.
|
||||
|
||||
@item
|
||||
IP addresses and ports are represented in slightly friendlier fashion
|
||||
than "network-endian integers".
|
||||
@item We can often avoid supplying an explicit length argument to
|
||||
functions because we already know how long the argument is.
|
||||
|
||||
@item IP addresses and ports are represented in slightly friendlier
|
||||
fashion than "network-endian integers".
|
||||
@end itemize
|
||||
|
||||
@node General Sockets
|
||||
@node general sockets
|
||||
@section General Sockets
|
||||
|
||||
@include class-sb-bsd-sockets-socket.texinfo
|
||||
@anchor{Class sb-bsd-sockets socket}
|
||||
@ttindex @sortas{socket sb-bsd-sockets} socket [sb-bsd-sockets]
|
||||
@deffn{Class} sb-bsd-sockets:socket
|
||||
Common superclass of all sockets, not meant to be
|
||||
directly instantiated.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets socket-bind}
|
||||
@ffindex @sortas{socket-bind sb-bsd-sockets} socket-bind [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:socket-bind socket &rest address
|
||||
Bind @code{socket} to @code{address}, which may vary according to socket family.
|
||||
For the INET family, pass @code{address} and @code{port} as two arguments; for local
|
||||
address family sockets, pass the filename string. See also @code{bind(2)}.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets socket-accept}
|
||||
@ffindex @sortas{socket-accept sb-bsd-sockets} socket-accept [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:socket-accept socket
|
||||
Perform the @code{accept(2)} call, returning a newly-created connected
|
||||
socket and the peer address as multiple values
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets socket-connect}
|
||||
@ffindex @sortas{socket-connect sb-bsd-sockets} socket-connect [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:socket-connect socket &rest address
|
||||
Perform the @code{connect(2)} call to connect @code{socket} to a remote @code{peer}.
|
||||
No useful return value.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets socket-peername}
|
||||
@ffindex @sortas{socket-peername sb-bsd-sockets} socket-peername [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:socket-peername socket
|
||||
Return @code{socket}'s peer; depending on the address family this may
|
||||
return multiple values
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets socket-name}
|
||||
@ffindex @sortas{socket-name sb-bsd-sockets} socket-name [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:socket-name socket
|
||||
Return the address (as vector of bytes) and port that @code{socket} is
|
||||
bound to, as multiple values.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets socket-receive}
|
||||
@ffindex @sortas{socket-receive sb-bsd-sockets} socket-receive [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:socket-receive socket buffer length &key oob peek waitall dontwait element-type
|
||||
Read @code{length} octets from @code{socket} into @code{buffer} (or a freshly-consed
|
||||
buffer if @code{nil}), using @code{recvfrom(2)}. If @code{length} is @code{nil}, the length of
|
||||
@code{buffer} is used, so at least one of these two arguments must be
|
||||
non-@code{nil}. If @code{buffer} is supplied, it had better be of an element type
|
||||
one octet wide. Returns the buffer, its length, and the address of the
|
||||
peer that sent it, as multiple values. On datagram sockets, sets
|
||||
@code{MSG_TRUNC} so that the actual packet length is returned even if
|
||||
the buffer was too small.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets socket-send}
|
||||
@ffindex @sortas{socket-send sb-bsd-sockets} socket-send [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:socket-send socket buffer length &key address external-format oob eor dontroute dontwait nosignal confirm more
|
||||
Send @code{length} octets from @code{buffer} into @code{socket}, using @code{sendto(2)}. If
|
||||
@code{buffer} is a string, it will converted to octets according to
|
||||
@code{external-format}. If @code{length} is @code{nil}, the length of the octet buffer is
|
||||
used. The format of @code{address} depends on the socket type (for example
|
||||
for INET domain sockets it would be a list of an IP address and a
|
||||
port). If no socket address is provided, @code{send(2)} will be called
|
||||
instead. Returns the number of octets written.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets socket-listen}
|
||||
@ffindex @sortas{socket-listen sb-bsd-sockets} socket-listen [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:socket-listen socket backlog
|
||||
Mark @code{socket} as willing to accept incoming connections. The
|
||||
integer @code{backlog} defines the maximum length that the queue of pending
|
||||
connections may grow to before new connection attempts are refused.
|
||||
See also @code{listen(2)}.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets socket-open-p}
|
||||
@ffindex @sortas{socket-open-p sb-bsd-sockets} socket-open-p [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:socket-open-p socket
|
||||
Return true if @code{socket} is open; otherwise, return false.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets socket-close}
|
||||
@ffindex @sortas{socket-close sb-bsd-sockets} socket-close [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:socket-close socket &key abort
|
||||
Close @code{socket}, unless it was already closed.
|
||||
|
||||
@include fun-sb-bsd-sockets-socket-bind.texinfo
|
||||
If @code{socket-make-stream} has been called, calls @code{close} using @code{abort} on that
|
||||
stream. Otherwise closes the socket file descriptor using @code{close(2)}.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets socket-shutdown}
|
||||
@ffindex @sortas{socket-shutdown sb-bsd-sockets} socket-shutdown [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:socket-shutdown socket &key direction
|
||||
Indicate that no communication in @code{direction} will be performed on
|
||||
@code{socket}.
|
||||
|
||||
@include fun-sb-bsd-sockets-socket-accept.texinfo
|
||||
@code{direction} has to be one of @code{:input}, @code{:output} or @code{:io}.
|
||||
|
||||
@include fun-sb-bsd-sockets-socket-connect.texinfo
|
||||
After a shutdown, no input and/or output of the indicated @code{direction}
|
||||
can be performed on @code{socket}.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets socket-make-stream}
|
||||
@ffindex @sortas{socket-make-stream sb-bsd-sockets} socket-make-stream [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:socket-make-stream socket &key input output element-type external-format buffering timeout auto-close serve-events
|
||||
Find or create a @code{stream} that can be used for IO on @code{socket} (which
|
||||
must be connected). Specify whether the stream is for @code{input}, @code{output},
|
||||
or both (it is an error to specify neither).
|
||||
|
||||
@include fun-sb-bsd-sockets-socket-peername.texinfo
|
||||
@code{element-type} and @code{external-format} are as per @code{open}.
|
||||
|
||||
@include fun-sb-bsd-sockets-socket-name.texinfo
|
||||
@code{timeout} specifies a read timeout for the stream.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets socket-error}
|
||||
@ffindex @sortas{socket-error sb-bsd-sockets} socket-error [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:socket-error where &optional errno
|
||||
Signal an appropriate error for syscall @code{where} and @code{errno}.
|
||||
|
||||
@include fun-sb-bsd-sockets-socket-receive.texinfo
|
||||
@code{where} should be a string naming the failed function.
|
||||
|
||||
@include fun-sb-bsd-sockets-socket-send.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-socket-listen.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-socket-open-p.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-socket-close.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-socket-shutdown.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-socket-make-stream.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-socket-error.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-non-blocking-mode.texinfo
|
||||
|
||||
@node Socket Options
|
||||
When supplied, @code{errno} should be the UNIX error number associated to the
|
||||
failed call. The default behavior is to use the current value of the
|
||||
errno variable.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets non-blocking-mode}
|
||||
@ffindex @sortas{non-blocking-mode sb-bsd-sockets} non-blocking-mode [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:non-blocking-mode socket
|
||||
Is @code{socket} in non-blocking mode?
|
||||
@end deffn
|
||||
@node socket options
|
||||
@section Socket Options
|
||||
|
||||
A subset of socket options are supported, using a fairly general
|
||||
framework which should make it simple to add more as required - see
|
||||
@file{SYS:CONTRIB;SB-BSD-SOCKETS:SOCKOPT.LISP} for details. The name
|
||||
framework which should make it simple to add more as required -- see
|
||||
@code{SYS:CONTRIB;SB-BSD-SOCKETS:SOCKOPT.LISP} for details. The name
|
||||
mapping from C is fairly straightforward: @code{SO_RCVLOWAT} becomes
|
||||
@code{sockopt-receive-low-water} and @code{(setf
|
||||
sockopt-receive-low-water)}.
|
||||
@code{sb-bsd-sockets:sockopt-receive-low-water} and @code{(setf
|
||||
sb-bsd-sockets:sockopt-receive-low-water)}.
|
||||
|
||||
@include fun-sb-bsd-sockets-sockopt-reuse-address.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-sockopt-keep-alive.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-sockopt-oob-inline.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-sockopt-bsd-compatible.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-sockopt-pass-credentials.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-sockopt-debug.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-sockopt-dont-route.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-sockopt-broadcast.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-sockopt-tcp-nodelay.texinfo
|
||||
|
||||
@node INET Domain Sockets
|
||||
@anchor{Function sb-bsd-sockets sockopt-reuse-address}
|
||||
@ffindex @sortas{sockopt-reuse-address sb-bsd-sockets} sockopt-reuse-address [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:sockopt-reuse-address socket
|
||||
Return the value of the SO-REUSEADDR socket option for @code{socket}. This can also be
|
||||
updated with @code{setf}.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets sockopt-keep-alive}
|
||||
@ffindex @sortas{sockopt-keep-alive sb-bsd-sockets} sockopt-keep-alive [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:sockopt-keep-alive socket
|
||||
Return the value of the SO-KEEPALIVE socket option for @code{socket}. This can also be
|
||||
updated with @code{setf}.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets sockopt-oob-inline}
|
||||
@ffindex @sortas{sockopt-oob-inline sb-bsd-sockets} sockopt-oob-inline [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:sockopt-oob-inline socket
|
||||
Return the value of the SO-OOBINLINE socket option for @code{socket}. This can also be
|
||||
updated with @code{setf}.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets sockopt-bsd-compatible}
|
||||
@ffindex @sortas{sockopt-bsd-compatible sb-bsd-sockets} sockopt-bsd-compatible [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:sockopt-bsd-compatible socket
|
||||
Return the value of the SO-BSDCOMPAT socket option for @code{socket}. This can also be
|
||||
updated with @code{setf}. Available only on Linux.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets sockopt-pass-credentials}
|
||||
@ffindex @sortas{sockopt-pass-credentials sb-bsd-sockets} sockopt-pass-credentials [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:sockopt-pass-credentials socket
|
||||
Return the value of the SO-PASSCRED socket option for @code{socket}. This can also be
|
||||
updated with @code{setf}. Available only on Linux.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets sockopt-debug}
|
||||
@ffindex @sortas{sockopt-debug sb-bsd-sockets} sockopt-debug [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:sockopt-debug socket
|
||||
Return the value of the SO-DEBUG socket option for @code{socket}. This can also be
|
||||
updated with @code{setf}.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets sockopt-dont-route}
|
||||
@ffindex @sortas{sockopt-dont-route sb-bsd-sockets} sockopt-dont-route [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:sockopt-dont-route socket
|
||||
Return the value of the SO-DONTROUTE socket option for @code{socket}. This can also be
|
||||
updated with @code{setf}.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets sockopt-broadcast}
|
||||
@ffindex @sortas{sockopt-broadcast sb-bsd-sockets} sockopt-broadcast [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:sockopt-broadcast socket
|
||||
Return the value of the SO-BROADCAST socket option for @code{socket}. This can also be
|
||||
updated with @code{setf}.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets sockopt-tcp-nodelay}
|
||||
@ffindex @sortas{sockopt-tcp-nodelay sb-bsd-sockets} sockopt-tcp-nodelay [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:sockopt-tcp-nodelay socket
|
||||
Return the value of the TCP-NODELAY socket option for @code{socket}. This can also be
|
||||
updated with @code{setf}.
|
||||
@end deffn
|
||||
@node inet domain sockets
|
||||
@section INET Domain Sockets
|
||||
|
||||
The TCP and UDP sockets that you know and love. Some representation
|
||||
issues:
|
||||
|
||||
@itemize
|
||||
@item IPv4 Internet addresses are represented by vectors of
|
||||
@code{(unsigned-byte 8)} (e.g. @code{#(127 0 0 1)}). Ports are just
|
||||
integers. No conversion between network- and host-order data is
|
||||
needed from the user of this package.
|
||||
|
||||
@item
|
||||
IPv4 Internet addresses are represented by vectors of
|
||||
@code{(unsigned-byte 8)} - viz. @code{#(127 0 0 1)}. Ports are just
|
||||
integers: 6010. No conversion between network- and host-order data is
|
||||
needed from the user of this package.
|
||||
|
||||
@item
|
||||
IPv6 Internet addresses are represented by vectors of 16
|
||||
@code{(unsigned-byte 8)} - viz. @code{#(0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
|
||||
1)}. Ports are just integers. As for IPv4 addresses, no conversion
|
||||
between network- and host-order data is needed from the user of this
|
||||
package.
|
||||
|
||||
@item
|
||||
Socket addresses are represented by the two values for address and port,
|
||||
so for example, @code{(socket-connect socket #(192 168 1 1) 80)} for
|
||||
IPv4 and @code{(socket-connect socket #(0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1)
|
||||
80)} for IPv6.
|
||||
@item IPv6 Internet addresses are represented by length 16 vectors of
|
||||
@code{(unsigned-byte 8)} (e.g. @code{#(0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1)}.
|
||||
Ports are just integers. As for IPv4 addresses, no conversion
|
||||
between network- and host-order data is needed from the user of
|
||||
this package.
|
||||
|
||||
@item Socket addresses are represented by the two values for address and
|
||||
port, so for example, @code{(sb-bsd-sockets:socket-connect socket #(192
|
||||
168 1 1) 80)} for IPv4 and @code{(sb-bsd-sockets:socket-connect socket
|
||||
#(0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1) 80)} for IPv6.
|
||||
@end itemize
|
||||
|
||||
@include class-sb-bsd-sockets-inet-socket.texinfo
|
||||
@anchor{Class sb-bsd-sockets inet-socket}
|
||||
@ttindex @sortas{inet-socket sb-bsd-sockets} inet-socket [sb-bsd-sockets]
|
||||
@deffn{Class} sb-bsd-sockets:inet-socket
|
||||
Class representing TCP and UDP over IPv4 sockets.
|
||||
|
||||
@include class-sb-bsd-sockets-inet6-socket.texinfo
|
||||
Examples:
|
||||
|
||||
@include fun-sb-bsd-sockets-make-inet-address.texinfo
|
||||
@example
|
||||
(make-instance 'sb-bsd-sockets:inet-socket :type :stream :protocol :tcp)
|
||||
|
||||
@include fun-sb-bsd-sockets-make-inet6-address.texinfo
|
||||
(make-instance 'sb-bsd-sockets:inet-socket :type :datagram :protocol :udp)
|
||||
@end example
|
||||
@end deffn
|
||||
@anchor{Class sb-bsd-sockets inet6-socket}
|
||||
@ttindex @sortas{inet6-socket sb-bsd-sockets} inet6-socket [sb-bsd-sockets]
|
||||
@deffn{Class} sb-bsd-sockets:inet6-socket
|
||||
Class representing TCP and UDP over IPv6 sockets.
|
||||
|
||||
@include fun-sb-bsd-sockets-get-protocol-by-name.texinfo
|
||||
Examples:
|
||||
|
||||
@node Local (Unix) Domain Sockets
|
||||
@section Local (Unix) Domain Sockets
|
||||
@example
|
||||
(make-instance 'sb-bsd-sockets:inet6-socket :type :stream :protocol :tcp)
|
||||
|
||||
(make-instance 'sb-bsd-sockets:inet6-socket :type :datagram :protocol :udp)
|
||||
@end example
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets make-inet-address}
|
||||
@ffindex @sortas{make-inet-address sb-bsd-sockets} make-inet-address [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:make-inet-address dotted-quads
|
||||
Return a vector of octets given a string @code{dotted-quads} in the format
|
||||
"127.0.0.1". Signals an error if the string is malformed.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets make-inet6-address}
|
||||
@ffindex @sortas{make-inet6-address sb-bsd-sockets} make-inet6-address [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:make-inet6-address colon-separated-integers
|
||||
Return a vector of octets given a string representation of an IPv6
|
||||
address @code{colon-separated-integers}. Signal an error if the string is
|
||||
malformed.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets get-protocol-by-name}
|
||||
@ffindex @sortas{get-protocol-by-name sb-bsd-sockets} get-protocol-by-name [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:get-protocol-by-name name
|
||||
Given a protocol name, return the protocol number, the protocol name, and
|
||||
a list of protocol aliases.
|
||||
@end deffn
|
||||
@node local domain sockets
|
||||
@section Local Domain Sockets
|
||||
|
||||
Local domain (@code{AF_LOCAL}) sockets are also known as Unix-domain
|
||||
sockets, but were renamed by POSIX presumably on the basis that they
|
||||
sockets but were renamed by POSIX presumably on the basis that they
|
||||
may be available on other systems too.
|
||||
|
||||
A local socket address is a string, which is used to create a node in
|
||||
the local filesystem. This means of course that they cannot be used
|
||||
across a network.
|
||||
|
||||
@include class-sb-bsd-sockets-local-socket.texinfo
|
||||
A local socket address is a string, which is used to create a node
|
||||
in the local filesystem. This means of course that they cannot be
|
||||
used across a network.
|
||||
|
||||
@anchor{Class sb-bsd-sockets local-socket}
|
||||
@ttindex @sortas{local-socket sb-bsd-sockets} local-socket [sb-bsd-sockets]
|
||||
@deffn{Class} sb-bsd-sockets:local-socket
|
||||
Class representing local domain (@code{AF_LOCAL}) sockets,
|
||||
also known as Unix-domain sockets.
|
||||
@end deffn
|
||||
A local abstract socket address is also a string the scope of which is
|
||||
the local machine. However, in contrast to a local socket address, there
|
||||
is no corresponding filesystem node.
|
||||
|
||||
@include class-sb-bsd-sockets-local-abstract-socket.texinfo
|
||||
|
||||
@node Name Service
|
||||
@anchor{Class sb-bsd-sockets local-abstract-socket}
|
||||
@ttindex @sortas{local-abstract-socket sb-bsd-sockets} local-abstract-socket [sb-bsd-sockets]
|
||||
@deffn{Class} sb-bsd-sockets:local-abstract-socket
|
||||
Class representing local domain (@code{AF_LOCAL}) sockets with
|
||||
addresses in the abstract namespace.
|
||||
@end deffn
|
||||
@node name service
|
||||
@section Name Service
|
||||
|
||||
Presently name service is implemented by calling out to the
|
||||
@code{getaddrinfo(3)} and @code{gethostinfo(3)}, or to
|
||||
@code{gethostbyname(3)} @code{gethostbyaddr(3)} on platforms where
|
||||
the preferred functions are not available. The exact details of
|
||||
the name resolving process (for example the choice of whether
|
||||
DNS or a hosts file is used for lookup) are platform dependent.
|
||||
@code{getaddrinfo(3)} and @code{gethostinfo(3)}, or to @code{gethostbyname(3)} and
|
||||
@code{gethostbyaddr(3)} on platforms where the preferred functions are
|
||||
not available. The exact details of the name resolving process (for
|
||||
example the choice of whether DNS or a hosts file is used for
|
||||
lookup) are platform dependent.
|
||||
|
||||
@c Direct links to the asynchronous @code{resolver(3)} routines would be
|
||||
@c nice to have eventually, so that we can do DNS lookups in parallel
|
||||
@c with other things.
|
||||
@anchor{Class sb-bsd-sockets host-ent}
|
||||
@ttindex @sortas{host-ent sb-bsd-sockets} host-ent [sb-bsd-sockets]
|
||||
@deffn{Class} sb-bsd-sockets:host-ent
|
||||
This class represents the results of an address lookup.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets get-host-by-name}
|
||||
@ffindex @sortas{get-host-by-name sb-bsd-sockets} get-host-by-name [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:get-host-by-name host-name
|
||||
Returns a @code{host-ent} instance for @code{host-name} or signals a @code{name-service-error}.
|
||||
|
||||
@include class-sb-bsd-sockets-host-ent.texinfo
|
||||
Another @code{host-ent} instance containing zero, one or more IPv6 addresses
|
||||
may be returned as a second return value.
|
||||
|
||||
@include fun-sb-bsd-sockets-get-host-by-name.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-get-host-by-address.texinfo
|
||||
|
||||
@include fun-sb-bsd-sockets-host-ent-address.texinfo
|
||||
@code{host-name} may also be an IP address in dotted quad notation or some other
|
||||
weird stuff - see getaddrinfo(3) for the details.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets get-host-by-address}
|
||||
@ffindex @sortas{get-host-by-address sb-bsd-sockets} get-host-by-address [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:get-host-by-address address
|
||||
Returns a @code{host-ent} instance for @code{address}, which should be a vector of
|
||||
(integer 0 255) with 4 elements in case of an IPv4 address and 16
|
||||
elements in case of an IPv6 address, or signals a @code{name-service-error}.
|
||||
See gethostbyaddr(3) for details.
|
||||
@end deffn
|
||||
@anchor{Function sb-bsd-sockets host-ent-address}
|
||||
@ffindex @sortas{host-ent-address sb-bsd-sockets} host-ent-address [sb-bsd-sockets]
|
||||
@deffn{Function} sb-bsd-sockets:host-ent-address host-ent
|
||||
Return some valid address for @code{host-ent}.
|
||||
@end deffn
|
||||
|
|
|
|||
|
|
@ -1,95 +1,336 @@
|
|||
@node sb-concurrency
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node sb concurrency
|
||||
@section sb-concurrency
|
||||
@cindex Concurrency
|
||||
@cindex Sb-concurrency
|
||||
|
||||
@menu
|
||||
* Queue: sb concurrency queue.
|
||||
* Mailbox (lock-free): sb concurrency mailbox.
|
||||
* Gates: sb concurrency gates.
|
||||
* Frlocks, aka Fast Read Locks: sb concurrency frlocks.
|
||||
@end menu
|
||||
|
||||
Additional data structures, synchronization primitives and tools for
|
||||
concurrent programming. Similiar to Java's @code{java.util.concurrent}
|
||||
package.
|
||||
|
||||
@page
|
||||
@anchor{Section sb-concurrency:queue}
|
||||
@node sb concurrency queue
|
||||
@subsection Queue
|
||||
@cindex Queue, lock-free
|
||||
|
||||
@code{sb-concurrency:queue} is a lock-free, thread-safe FIFO queue
|
||||
datatype.
|
||||
@*@*
|
||||
The implementation is based on @cite{An Optimistic Approach to
|
||||
Lock-Free FIFO Queues} by Edya Ladan-Mozes and Nir Shavit.
|
||||
@*@*
|
||||
|
||||
The implementation is based on @emph{An Optimistic Approach to Lock-Free
|
||||
FIFO Queues} by Edya Ladan-Mozes and Nir Shavit.
|
||||
|
||||
Before SBCL 1.0.38, this implementation resided in its own contrib
|
||||
(@pxref{sb-queue}) which is still provided for backwards-compatibility
|
||||
but which has since been deprecated.
|
||||
(see @ref{sb queue}), which is still provided for
|
||||
backwards-compatibility, but which has since been deprecated.
|
||||
|
||||
@include struct-sb-concurrency-queue.texinfo
|
||||
@anchor{Structure sb-concurrency queue}
|
||||
@ttindex @sortas{queue sb-concurrency} queue [sb-concurrency]
|
||||
@deffn{Structure} sb-concurrency:queue
|
||||
Lock-free thread safe FIFO queue.
|
||||
|
||||
@include fun-sb-concurrency-dequeue.texinfo
|
||||
@include fun-sb-concurrency-enqueue.texinfo
|
||||
@include fun-sb-concurrency-list-queue-contents.texinfo
|
||||
@include fun-sb-concurrency-make-queue.texinfo
|
||||
@include fun-sb-concurrency-queue-count.texinfo
|
||||
@include fun-sb-concurrency-queue-empty-p.texinfo
|
||||
@include fun-sb-concurrency-queue-name.texinfo
|
||||
@include fun-sb-concurrency-queuep.texinfo
|
||||
|
||||
@page
|
||||
Use @code{enqueue} to add objects to the queue, and @code{dequeue} to remove them.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency dequeue}
|
||||
@ffindex @sortas{dequeue sb-concurrency} dequeue [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:dequeue queue
|
||||
Retrieves the oldest value in @code{queue} and returns it as the primary value,
|
||||
and @code{t} as secondary value. If the queue is empty, returns @code{nil} as both primary
|
||||
and secondary value.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency enqueue}
|
||||
@ffindex @sortas{enqueue sb-concurrency} enqueue [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:enqueue value queue
|
||||
Adds @code{value} to the end of @code{queue}. Returns @code{value}.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency list-queue-contents}
|
||||
@ffindex @sortas{list-queue-contents sb-concurrency} list-queue-contents [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:list-queue-contents queue
|
||||
Returns the contents of @code{queue} as a list without removing them from the
|
||||
@code{queue}. Mainly useful for manual examination of queue state, as the list may be
|
||||
out of date by the time it is returned, and concurrent dequeue operations may
|
||||
in the worse case force the queue-traversal to be restarted several times.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency make-queue}
|
||||
@ffindex @sortas{make-queue sb-concurrency} make-queue [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:make-queue &key name initial-contents
|
||||
Returns a new @code{queue} with @code{name} and contents of the @code{initial-contents}
|
||||
sequence enqueued.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency queue-count}
|
||||
@ffindex @sortas{queue-count sb-concurrency} queue-count [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:queue-count queue
|
||||
Returns the number of objects in @code{queue}. Mainly useful for manual
|
||||
examination of queue state, and in @code{print-object} methods: inefficient as it
|
||||
must walk the entire queue.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency queue-empty-p}
|
||||
@ffindex @sortas{queue-empty-p sb-concurrency} queue-empty-p [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:queue-empty-p queue
|
||||
Returns @code{t} if @code{queue} is empty, @code{nil} otherwise.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency queue-name}
|
||||
@ffindex @sortas{queue-name sb-concurrency} queue-name [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:queue-name instance
|
||||
Name of a @code{queue}. Can be assigned to using @code{setf}. Queue names
|
||||
can be arbitrary printable objects, and need not be unique.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency queuep}
|
||||
@ffindex @sortas{queuep sb-concurrency} queuep [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:queuep object
|
||||
Returns true if argument is a @code{queue}, @code{nil} otherwise.
|
||||
@end deffn
|
||||
@node sb concurrency mailbox
|
||||
@subsection Mailbox (lock-free)
|
||||
@cindex Mailbox, lock-free
|
||||
|
||||
@code{sb-concurrency:mailbox} is a lock-free message queue where one
|
||||
or multiple ends can send messages to one or multiple receivers. The
|
||||
difference to @ref{Section sb-concurrency:queue, queues} is that the receiving
|
||||
end may block until a message arrives.
|
||||
@*@*
|
||||
Built on top of the @ref{Structure sb-concurrency queue, queue} implementation.
|
||||
@code{sb-concurrency:mailbox} is a lock-free message queue where one or
|
||||
multiple ends can send messages to one or multiple receivers. The
|
||||
difference to @ref{sb concurrency queue} is that the receiving end may
|
||||
block until a message arrives.
|
||||
|
||||
@include struct-sb-concurrency-mailbox.texinfo
|
||||
Built on top of the @ref{sb concurrency queue} implementation.
|
||||
|
||||
@include fun-sb-concurrency-list-mailbox-messages.texinfo
|
||||
@include fun-sb-concurrency-mailbox-count.texinfo
|
||||
@include fun-sb-concurrency-mailbox-empty-p.texinfo
|
||||
@include fun-sb-concurrency-mailbox-name.texinfo
|
||||
@include fun-sb-concurrency-mailboxp.texinfo
|
||||
@include fun-sb-concurrency-make-mailbox.texinfo
|
||||
@include fun-sb-concurrency-receive-message.texinfo
|
||||
@include fun-sb-concurrency-receive-message-no-hang.texinfo
|
||||
@include fun-sb-concurrency-receive-pending-messages.texinfo
|
||||
@include fun-sb-concurrency-send-message.texinfo
|
||||
@anchor{Structure sb-concurrency mailbox}
|
||||
@ttindex @sortas{mailbox sb-concurrency} mailbox [sb-concurrency]
|
||||
@deffn{Structure} sb-concurrency:mailbox
|
||||
Mailbox aka message queue.
|
||||
|
||||
@page
|
||||
@anchor{Section sb-concurrency:gate}
|
||||
@code{send-message} adds a message to the mailbox, @code{receive-message} waits till
|
||||
a message becomes available, whereas @code{receive-message-no-hang} is a non-blocking
|
||||
variant, and @code{receive-pending-messages} empties the entire mailbox in one go.
|
||||
|
||||
Messages can be arbitrary objects.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency list-mailbox-messages}
|
||||
@ffindex @sortas{list-mailbox-messages sb-concurrency} list-mailbox-messages [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:list-mailbox-messages mailbox
|
||||
Returns a fresh list containing all the messages in @code{mailbox}. Does not
|
||||
remove messages from the mailbox.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency mailbox-count}
|
||||
@ffindex @sortas{mailbox-count sb-concurrency} mailbox-count [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:mailbox-count mailbox
|
||||
Returns the number of messages currently in @code{mailbox}.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency mailbox-empty-p}
|
||||
@ffindex @sortas{mailbox-empty-p sb-concurrency} mailbox-empty-p [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:mailbox-empty-p mailbox
|
||||
Returns true if @code{mailbox} is currently empty, @code{nil} otherwise.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency mailbox-name}
|
||||
@ffindex @sortas{mailbox-name sb-concurrency} mailbox-name [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:mailbox-name instance
|
||||
Name of a @code{mailbox}. @code{setf}able.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency mailboxp}
|
||||
@ffindex @sortas{mailboxp sb-concurrency} mailboxp [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:mailboxp object
|
||||
Returns true if argument is a @code{mailbox}, @code{nil} otherwise.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency make-mailbox}
|
||||
@ffindex @sortas{make-mailbox sb-concurrency} make-mailbox [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:make-mailbox &key name initial-contents
|
||||
Returns a new @code{mailbox} with messages in @code{initial-contents} enqueued.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency receive-message}
|
||||
@ffindex @sortas{receive-message sb-concurrency} receive-message [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:receive-message mailbox &key timeout
|
||||
Removes the oldest message from @code{mailbox} and returns it as the primary
|
||||
value, and a secondary value of @code{t}. If @code{mailbox} is empty waits until a message
|
||||
arrives.
|
||||
|
||||
If @code{timeout} is provided, and no message arrives within the specified interval,
|
||||
returns primary and secondary value of @code{nil}.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency receive-message-no-hang}
|
||||
@ffindex @sortas{receive-message-no-hang sb-concurrency} receive-message-no-hang [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:receive-message-no-hang mailbox
|
||||
The non-blocking variant of @code{receive-message}. Returns two values,
|
||||
the message removed from @code{mailbox}, and a flag specifying whether a
|
||||
message could be received.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency receive-pending-messages}
|
||||
@ffindex @sortas{receive-pending-messages sb-concurrency} receive-pending-messages [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:receive-pending-messages mailbox &optional n
|
||||
Removes and returns all (or at most @code{n}) currently pending messages
|
||||
from @code{mailbox}, or returns @code{nil} if no messages are pending.
|
||||
|
||||
@quotation
|
||||
@emph{Note}: Concurrent threads may be snarfing messages during the run
|
||||
of this function, so even @code{x} and @code{y} appearing right next to each
|
||||
other in the result does not necessarily mean that @code{y} was the
|
||||
message sent right after @code{x}.
|
||||
@end quotation
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency send-message}
|
||||
@ffindex @sortas{send-message sb-concurrency} send-message [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:send-message mailbox message
|
||||
Adds a @code{message} to @code{mailbox}. Message can be any object.
|
||||
@end deffn
|
||||
@node sb concurrency gates
|
||||
@subsection Gates
|
||||
@cindex Gate
|
||||
|
||||
@code{sb-concurrency:gate} is a synchronization object suitable for when
|
||||
multiple threads must wait for a single event before proceeding.
|
||||
|
||||
@include struct-sb-concurrency-gate.texinfo
|
||||
@anchor{Structure sb-concurrency gate}
|
||||
@ttindex @sortas{gate sb-concurrency} gate [sb-concurrency]
|
||||
@deffn{Structure} sb-concurrency:gate
|
||||
@code{gate} type. Gates are synchronization constructs suitable for making
|
||||
multiple threads wait for single event before proceeding.
|
||||
|
||||
@include fun-sb-concurrency-close-gate.texinfo
|
||||
@include fun-sb-concurrency-gate-name.texinfo
|
||||
@include fun-sb-concurrency-gate-open-p.texinfo
|
||||
@include fun-sb-concurrency-gatep.texinfo
|
||||
@include fun-sb-concurrency-make-gate.texinfo
|
||||
@include fun-sb-concurrency-open-gate.texinfo
|
||||
@include fun-sb-concurrency-wait-on-gate.texinfo
|
||||
|
||||
@page
|
||||
@anchor{Section sb-concurrency:frlock}
|
||||
Use @code{wait-on-gate} to wait for a gate to open, @code{open-gate} to open one,
|
||||
and @code{close-gate} to close an open gate. @code{gate-open-p} can be used to test
|
||||
the state of a gate without blocking.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency close-gate}
|
||||
@ffindex @sortas{close-gate sb-concurrency} close-gate [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:close-gate gate
|
||||
Closes @code{gate}. Returns @code{t} if the gate was previously open, and @code{nil}
|
||||
if the gate was already closed.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency gate-name}
|
||||
@ffindex @sortas{gate-name sb-concurrency} gate-name [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:gate-name instance
|
||||
Name of a @code{gate}. @code{setf}able.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency gate-open-p}
|
||||
@ffindex @sortas{gate-open-p sb-concurrency} gate-open-p [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:gate-open-p gate
|
||||
Returns true if @code{gate} is open.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency gatep}
|
||||
@ffindex @sortas{gatep sb-concurrency} gatep [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:gatep object
|
||||
Returns true if the argument is a @code{gate}.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency make-gate}
|
||||
@ffindex @sortas{make-gate sb-concurrency} make-gate [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:make-gate &key name open
|
||||
Makes a new gate. Gate will be initially open if @code{open} is true, and closed if @code{open}
|
||||
is @code{nil} (the default.) @code{name}, if provided, is the name of the gate, used when printing
|
||||
the gate.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency open-gate}
|
||||
@ffindex @sortas{open-gate sb-concurrency} open-gate [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:open-gate gate
|
||||
Opens @code{gate}. Returns @code{t} if the gate was previously closed, and @code{nil}
|
||||
if the gate was already open.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency wait-on-gate}
|
||||
@ffindex @sortas{wait-on-gate sb-concurrency} wait-on-gate [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:wait-on-gate gate &key timeout
|
||||
Waits for @code{gate} to open, or @code{timeout} seconds to pass. Returns @code{t}
|
||||
if the gate was opened in time, and @code{nil} otherwise.
|
||||
@end deffn
|
||||
@node sb concurrency frlocks
|
||||
@subsection Frlocks, aka Fast Read Locks
|
||||
@cindex Frlock
|
||||
@cindex Fast Read Lock
|
||||
|
||||
@include struct-sb-concurrency-frlock.texinfo
|
||||
@anchor{Structure sb-concurrency frlock}
|
||||
@ttindex @sortas{frlock sb-concurrency} frlock [sb-concurrency]
|
||||
@deffn{Structure} sb-concurrency:frlock
|
||||
FRlock, aka Fast Read Lock.
|
||||
|
||||
@include macro-sb-concurrency-frlock-read.texinfo
|
||||
@include macro-sb-concurrency-frlock-write.texinfo
|
||||
Fast Read Locks allow multiple readers and one potential writer to operate in
|
||||
parallel while providing for consistency for readers and mutual exclusion for
|
||||
writers.
|
||||
|
||||
@include fun-sb-concurrency-make-frlock.texinfo
|
||||
@include fun-sb-concurrency-frlock-name.texinfo
|
||||
Readers gain entry to protected regions without waiting, but need to retry if
|
||||
a writer operated inside the region while they were reading. This makes frlocks
|
||||
very efficient when readers are much more common than writers.
|
||||
|
||||
@include fun-sb-concurrency-frlock-read-begin.texinfo
|
||||
@include fun-sb-concurrency-frlock-read-end.texinfo
|
||||
@include fun-sb-concurrency-grab-frlock-write-lock.texinfo
|
||||
@include fun-sb-concurrency-release-frlock-write-lock.texinfo
|
||||
FRlocks are @emph{not} suitable when it is not safe at all for readers and writers
|
||||
to operate on the same data in parallel: they provide consistency, not
|
||||
exclusion between readers and writers. Hence using an frlock to e.g. protect
|
||||
an SBCL hash-table is unsafe. If multiple readers operating in parallel with
|
||||
a writer would be safe but inconsistent without a lock, frlocks are suitable.
|
||||
|
||||
The recommended interface to use is @code{frlock-read} and @code{frlock-write}, but those
|
||||
needing it can also use a lower-level interface.
|
||||
|
||||
Example:
|
||||
|
||||
@example
|
||||
;; Values returned by FOO are always consistent so that
|
||||
;; the third value is the sum of the two first ones.
|
||||
(let ((a 0)
|
||||
(b 0)
|
||||
(c 0)
|
||||
(lk (make-frlock)))
|
||||
(defun foo ()
|
||||
(frlock-read (lk) a b c))
|
||||
(defun bar (x y)
|
||||
(frlock-write (lk)
|
||||
(setf a x
|
||||
b y
|
||||
c (+ x y)))))
|
||||
@end example
|
||||
@end deffn
|
||||
@anchor{Macro sb-concurrency frlock-read}
|
||||
@ffindex @sortas{frlock-read sb-concurrency} frlock-read [sb-concurrency]
|
||||
@deffn{Macro} sb-concurrency:frlock-read (frlock) &body value-forms
|
||||
Evaluates @code{value-forms} under @code{frlock} till it obtains a consistent
|
||||
set, and returns that as multiple values.
|
||||
@end deffn
|
||||
@anchor{Macro sb-concurrency frlock-write}
|
||||
@ffindex @sortas{frlock-write sb-concurrency} frlock-write [sb-concurrency]
|
||||
@deffn{Macro} sb-concurrency:frlock-write (frlock &key wait-p timeout) &body body
|
||||
Executes @code{body} while holding @code{frlock} for writing.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency make-frlock}
|
||||
@ffindex @sortas{make-frlock sb-concurrency} make-frlock [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:make-frlock &key name
|
||||
Returns a new @code{frlock} with @code{name}.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency frlock-name}
|
||||
@ffindex @sortas{frlock-name sb-concurrency} frlock-name [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:frlock-name instance
|
||||
Name of an @code{frlock}. @code{setf}able.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency frlock-read-begin}
|
||||
@ffindex @sortas{frlock-read-begin sb-concurrency} frlock-read-begin [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:frlock-read-begin frlock
|
||||
Start a read sequence on @code{frlock}. Returns a read-token and an epoch to be
|
||||
validated later.
|
||||
|
||||
Using @code{frlock-read} instead is recommended.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency frlock-read-end}
|
||||
@ffindex @sortas{frlock-read-end sb-concurrency} frlock-read-end [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:frlock-read-end frlock
|
||||
Ends a read sequence on @code{frlock}. Returns a token and an epoch. If the token
|
||||
and epoch are @code{eql} to the read-token and epoch returned by @code{frlock-read-begin},
|
||||
the values read under the @code{frlock} are consistent and can be used: if the values
|
||||
differ, the values are inconsistent and the read must be restated.
|
||||
|
||||
Using @code{frlock-read} instead is recommended.
|
||||
|
||||
Example:
|
||||
|
||||
@example
|
||||
(multiple-value-bind (t0 e0) (frlock-read-begin *fr*)
|
||||
(let ((a (get-a))
|
||||
(b (get-b)))
|
||||
(multiple-value-bind (t1 e1) (frlock-read-end *fr*)
|
||||
(if (and (eql t0 t1) (eql e0 e1))
|
||||
(list :a a :b b)
|
||||
:aborted))))
|
||||
@end example
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency grab-frlock-write-lock}
|
||||
@ffindex @sortas{grab-frlock-write-lock sb-concurrency} grab-frlock-write-lock [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:grab-frlock-write-lock frlock &key wait-p timeout
|
||||
Acquires @code{frlock} for writing, invalidating existing and future read-tokens
|
||||
for the duration. Returns @code{t} on success, and @code{nil} if the lock wasn't acquired
|
||||
due to e.g. a timeout. Using @code{frlock-write} instead is recommended.
|
||||
@end deffn
|
||||
@anchor{Function sb-concurrency release-frlock-write-lock}
|
||||
@ffindex @sortas{release-frlock-write-lock sb-concurrency} release-frlock-write-lock [sb-concurrency]
|
||||
@deffn{Function} sb-concurrency:release-frlock-write-lock frlock
|
||||
Releases @code{frlock} after writing, allowing valid read-tokens to be acquired again.
|
||||
Signals an error if the current thread doesn't hold @code{frlock} for writing. Using @code{frlock-write}
|
||||
instead is recommended.
|
||||
@end deffn
|
||||
|
|
|
|||
|
|
@ -1,19 +1,20 @@
|
|||
@node sb-cover
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node sb cover
|
||||
@section sb-cover
|
||||
@cindex Code Coverage
|
||||
|
||||
The @code{sb-cover} module provides a code coverage tool for SBCL. The
|
||||
tool has support for expression coverage, and for some branch coverage.
|
||||
Coverage reports are only generated for code compiled using
|
||||
@code{compile-file} with the value of the
|
||||
tool has support for expression coverage, and for some branch
|
||||
coverage. Coverage reports are only generated for code compiled
|
||||
using @code{compile-file} with the value of the
|
||||
@code{sb-cover:store-coverage-data} optimization quality set to 3.
|
||||
|
||||
As of SBCL 1.0.6 @code{sb-cover} is still experimental, and the
|
||||
As of SBCL 1.0.6, @code{sb-cover} is still experimental, and the
|
||||
interfaces documented here might change in later versions.
|
||||
|
||||
@subsection Example Usage
|
||||
How to use it:
|
||||
|
||||
@lisp
|
||||
@example
|
||||
;;; Load SB-COVER
|
||||
(require :sb-cover)
|
||||
|
||||
|
|
@ -32,27 +33,76 @@ interfaces documented here might change in later versions.
|
|||
|
||||
;;; Turn off instrumentation
|
||||
(declaim (optimize (sb-cover:store-coverage-data 0)))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
@c @subsection Output
|
||||
@c Write some documentation about how to interpret the results
|
||||
@anchor{Function sb-cover report}
|
||||
@ffindex @sortas{report sb-cover} report [sb-cover]
|
||||
@deffn{Function} sb-cover:report directory &key form-mode if-matches external-format
|
||||
Print a code coverage report of all instrumented files into @code{directory}.
|
||||
If @code{directory} does not exist, it will be created. The main report will be
|
||||
printed to the file cover-index.html. The external format of the source
|
||||
files can be specified with the @code{external-format} parameter.
|
||||
|
||||
@subsection Functions
|
||||
If the keyword argument @code{:form-mode} has the value @code{:car}, the annotations
|
||||
in the coverage report will be placed on the @code{car}s of any cons-forms,
|
||||
while if it has the value @code{:whole} the whole form will be annotated (the
|
||||
default). The former mode shows explicitly which forms were
|
||||
instrumented, while the latter mode is generally easier to read.
|
||||
|
||||
@include fun-sb-cover-report.texinfo
|
||||
|
||||
@include fun-sb-cover-reset-coverage.texinfo
|
||||
|
||||
@include fun-sb-cover-clear-coverage.texinfo
|
||||
|
||||
@include fun-sb-cover-save-coverage.texinfo
|
||||
|
||||
@include fun-sb-cover-save-coverage-in-file.texinfo
|
||||
|
||||
@include fun-sb-cover-restore-coverage.texinfo
|
||||
|
||||
@include fun-sb-cover-restore-coverage-from-file.texinfo
|
||||
|
||||
@include fun-sb-cover-merge-coverage.texinfo
|
||||
|
||||
@include fun-sb-cover-merge-coverage-from-file.texinfo
|
||||
The keyword argument @code{if-matches} should be a designator for a function
|
||||
of one argument, called for the namestring of each file with code
|
||||
coverage info. If it returns true, the file's info is included in the
|
||||
report, otherwise ignored. The default value is @code{cl:identity}.
|
||||
@end deffn
|
||||
@anchor{Function sb-cover reset-coverage}
|
||||
@ffindex @sortas{reset-coverage sb-cover} reset-coverage [sb-cover]
|
||||
@deffn{Function} sb-cover:reset-coverage &optional object
|
||||
Reset all coverage data back to the @code{Not executed} state.
|
||||
@end deffn
|
||||
@anchor{Function sb-cover clear-coverage}
|
||||
@ffindex @sortas{clear-coverage sb-cover} clear-coverage [sb-cover]
|
||||
@deffn{Function} sb-cover:clear-coverage
|
||||
Clear all files from the coverage database. The files will be re-entered
|
||||
into the database when the FASL files (produced by compiling
|
||||
@code{store-coverage-data} optimization policy set to 3) are loaded again into the
|
||||
image.
|
||||
@end deffn
|
||||
@anchor{Function sb-cover save-coverage}
|
||||
@ffindex @sortas{save-coverage sb-cover} save-coverage [sb-cover]
|
||||
@deffn{Function} sb-cover:save-coverage
|
||||
Returns an opaque representation of the current code coverage state.
|
||||
The only operation that may be done on the state is passing it to
|
||||
@code{restore-coverage}. The representation is guaranteed to be readably printable.
|
||||
A representation that has been printed and read back will work identically
|
||||
in @code{restore-coverage}.
|
||||
@end deffn
|
||||
@anchor{Function sb-cover save-coverage-in-file}
|
||||
@ffindex @sortas{save-coverage-in-file sb-cover} save-coverage-in-file [sb-cover]
|
||||
@deffn{Function} sb-cover:save-coverage-in-file pathname
|
||||
Call @code{save-coverage} and write the results of that operation into the
|
||||
file designated by @code{pathname}.
|
||||
@end deffn
|
||||
@anchor{Function sb-cover restore-coverage}
|
||||
@ffindex @sortas{restore-coverage sb-cover} restore-coverage [sb-cover]
|
||||
@deffn{Function} sb-cover:restore-coverage coverage-state
|
||||
Restore the code coverage data back to an earlier state produced by
|
||||
@code{save-coverage}.
|
||||
@end deffn
|
||||
@anchor{Function sb-cover restore-coverage-from-file}
|
||||
@ffindex @sortas{restore-coverage-from-file sb-cover} restore-coverage-from-file [sb-cover]
|
||||
@deffn{Function} sb-cover:restore-coverage-from-file pathname
|
||||
@code{read} the contents of the file designated by @code{pathname} and pass the
|
||||
result to @code{restore-coverage}.
|
||||
@end deffn
|
||||
@anchor{Function sb-cover merge-coverage}
|
||||
@ffindex @sortas{merge-coverage sb-cover} merge-coverage [sb-cover]
|
||||
@deffn{Function} sb-cover:merge-coverage coverage-state
|
||||
Merge the code coverage data to include covered code from an earlier
|
||||
state produced by @code{save-coverage}.
|
||||
@end deffn
|
||||
@anchor{Function sb-cover merge-coverage-from-file}
|
||||
@ffindex @sortas{merge-coverage-from-file sb-cover} merge-coverage-from-file [sb-cover]
|
||||
@deffn{Function} sb-cover:merge-coverage-from-file pathname
|
||||
@code{read} the contents of the file designated by @code{pathname} and pass the
|
||||
result to @code{merge-coverage}.
|
||||
@end deffn
|
||||
|
|
|
|||
|
|
@ -1,42 +1,47 @@
|
|||
@node sb-grovel
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node sb grovel
|
||||
@section sb-grovel
|
||||
@cindex Foreign Function Interface, generation
|
||||
|
||||
@menu
|
||||
* Using sb-grovel in your own ASDF System: using sb grovel.
|
||||
* Contents of a grovel-constants-file: sb grovel constants file.
|
||||
* Programming with sb-grovel's structure types: sb grovel structures.
|
||||
* Traps and Pitfalls: sb grovel traps.
|
||||
@end menu
|
||||
|
||||
The @code{sb-grovel} module helps in generation of foreign function
|
||||
interfaces. It aids in extracting constants' values from the C
|
||||
compiler and in generating SB-ALIEN structure and union types,
|
||||
@pxref{Defining Foreign Types}.
|
||||
compiler and in generating sb-alien structure and union types,
|
||||
@ref{defining foreign types}.
|
||||
|
||||
The ASDF(@uref{http://www.cliki.net/ASDF}) component type
|
||||
GROVEL-CONSTANTS-FILE has its PERFORM
|
||||
@c @xref for PERFORM when asdf manual is included?
|
||||
operation defined to write out a C source file, compile it, and run
|
||||
it. The output from this program is Lisp, which is then itself
|
||||
compiled and loaded.
|
||||
The ASDF (@url{http://www.cliki.net/ASDF}) component type
|
||||
GROVEL-CONSTANTS-FILE has its @code{asdf:perform} operation defined to
|
||||
write out a C source file, compile it, and run it. The output from
|
||||
this program is Lisp, which is then itself compiled and loaded.
|
||||
|
||||
sb-grovel is used in a few contributed modules, and it is currently
|
||||
compatible only to SBCL. However, if you want to use it, here are a
|
||||
few directions.
|
||||
@code{sb-grovel} is used in a few contributed modules, and it is
|
||||
currently compatible only to SBCL. However, if you want to use it,
|
||||
here are a few directions.
|
||||
|
||||
@subsection Using sb-grovel in your own ASDF system
|
||||
@node using sb grovel
|
||||
@subsection Using sb-grovel in your own ASDF System
|
||||
|
||||
@enumerate
|
||||
@itemize
|
||||
@item Create a Lisp package for the foreign constants/functions to go
|
||||
@end itemize
|
||||
into.
|
||||
|
||||
@item
|
||||
Create a Lisp package for the foreign constants/functions to go into.
|
||||
@itemize
|
||||
@item Make your system depend on the @code{sb-grovel} system.
|
||||
|
||||
@item
|
||||
Make your system depend on the 'sb-grovel system.
|
||||
@item Create a grovel-constants data file -- for an example, see
|
||||
@code{example-constants.lisp} in the @code{contrib/sb-grovel/} directory in
|
||||
the SBCL source distribution.
|
||||
|
||||
@item
|
||||
Create a grovel-constants data file - for an example, see
|
||||
example-constants.lisp in the contrib/sb-grovel/ directory in the SBCL
|
||||
source distribution.
|
||||
@item Add it as a component in your system. For example:
|
||||
|
||||
@item
|
||||
Add it as a component in your system. e.g.
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(eval-when (:compile-toplevel :load-toplevel :execute)
|
||||
(require :sb-grovel))
|
||||
|
||||
|
|
@ -53,34 +58,35 @@ Add it as a component in your system. e.g.
|
|||
((:file "defpackage")
|
||||
(grovel-constants-file "example-constants"
|
||||
:package :example-package)))))
|
||||
@end lisp
|
||||
@end example
|
||||
@end itemize
|
||||
|
||||
Make sure to specify the package you chose in step 1
|
||||
Make sure to specify the package you chose in step 1.
|
||||
|
||||
@item
|
||||
Build stuff.
|
||||
|
||||
@end enumerate
|
||||
@itemize
|
||||
@item Build stuff.
|
||||
@end itemize
|
||||
|
||||
@node sb grovel constants file
|
||||
@subsection Contents of a grovel-constants-file
|
||||
|
||||
The grovel-constants-file, typically named @code{constants.lisp},
|
||||
comprises lisp expressions describing the foreign things that you want
|
||||
to grovel for. A @code{constants.lisp} file contains two sections:
|
||||
comprises lisp expressions describing the foreign things that you
|
||||
want to grovel for. A @code{constants.lisp} file contains two sections:
|
||||
|
||||
@itemize
|
||||
@item
|
||||
a list of headers to include in the C program, for example:
|
||||
@lisp
|
||||
@item a list of headers to include in the C program, for example:
|
||||
|
||||
@example
|
||||
("sys/types.h" "sys/socket.h" "sys/stat.h" "unistd.h" "sys/un.h"
|
||||
"netinet/in.h" "netinet/in_systm.h" "netinet/ip.h" "net/if.h"
|
||||
"netdb.h" "errno.h" "netinet/tcp.h" "fcntl.h" "signal.h" )
|
||||
@end lisp
|
||||
"netdb.h" "errno.h" "netinet/tcp.h" "fcntl.h" "signal.h")
|
||||
@end example
|
||||
|
||||
@item
|
||||
A list of sb-grovel clauses describing the things you want to grovel
|
||||
from the C compiler, for example:
|
||||
@lisp
|
||||
@item A list of sb-grovel clauses describing the things you want to
|
||||
grovel from the C compiler, for example:
|
||||
|
||||
@example
|
||||
((:integer af-local
|
||||
#+(or sunos solaris) "AF_UNIX"
|
||||
#-(or sunos solaris) "AF_LOCAL"
|
||||
|
|
@ -89,149 +95,151 @@ from the C compiler, for example:
|
|||
(integer dev "dev_t" "st_dev")
|
||||
(integer atime "time_t" "st_atime")))
|
||||
(:function getpid ("getpid" int )))
|
||||
@end lisp
|
||||
@end example
|
||||
@end itemize
|
||||
|
||||
There are two types of things that sb-grovel can sensibly extract from
|
||||
the C compiler: constant integers and structure layouts. It is also
|
||||
possible to define foreign functions in the constants.lisp file, but
|
||||
these definitions don't use any information from the C program; they
|
||||
expand directly to @code{sb-alien:define-alien-routine}
|
||||
(@pxref{The define-alien-routine Macro}) forms.
|
||||
There are two types of things that sb-grovel can sensibly extract
|
||||
from the C compiler: constant integers and structure layouts. It is
|
||||
also possible to define foreign functions in the constants.lisp
|
||||
file, but these definitions don't use any information from the C
|
||||
program; they expand directly to @code{sb-alien:define-alien-routine}
|
||||
forms.
|
||||
|
||||
Here's how to use the grovel clauses:
|
||||
|
||||
@itemize
|
||||
@item
|
||||
@code{:integer} - constant expressions in C. Used in this form:
|
||||
@lisp
|
||||
@item @code{:integer}: constant expressions in C. Used in this form:
|
||||
|
||||
@example
|
||||
(:integer lisp-variable-name "C expression" &optional doc export)
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
@code{"C expression"} will be typically be the name of a constant. But
|
||||
other forms are possible.
|
||||
@code{"C expression"} will be typically be the name of a constant,
|
||||
but other forms are possible.
|
||||
|
||||
@item
|
||||
@code{:enum}
|
||||
@lisp
|
||||
@item @code{:enum}:
|
||||
|
||||
@example
|
||||
(:enum lisp-type-name ((lisp-enumerated-name c-enumerated-name) ...)))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
An @code{sb-alien:enum} type with name @code{lisp-type-name} will be defined.
|
||||
The symbols are the @code{lisp-enumerated-name}s, and the values
|
||||
are grovelled from the @code{c-enumerated-name}s.
|
||||
An @code{sb-alien:enum} type with name @code{lisp-type-name} will be
|
||||
defined. The symbols are the @code{lisp-enumerated-name}s, and the
|
||||
values are grovelled from the @code{c-enumerated-name}s.
|
||||
|
||||
@item
|
||||
@code{:structure} - alien structure definitions look like this:
|
||||
@lisp
|
||||
@item @code{:structure}: alien structure definitions look like this:
|
||||
|
||||
@example
|
||||
(:structure lisp-struct-name ("struct c_structure"
|
||||
(type-designator lisp-element-name
|
||||
"c_element_type" "c_element_name"
|
||||
:distrust-length nil)
|
||||
; ...
|
||||
))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
@code{type-designator} is a reference to a type whose size (and type
|
||||
constraints) will be groveled for. sb-grovel accepts a form of type
|
||||
designator that doesn't quite conform to either lisp nor sb-alien's
|
||||
type specifiers. Here's a list of type designators that sb-grovel
|
||||
currently accepts:
|
||||
constraints) will be groveled for. sb-grovel accepts a form of
|
||||
type designator that doesn't quite conform to either lisp nor
|
||||
sb-alien's type specifiers. Here's a list of type designators
|
||||
that sb-grovel currently accepts:
|
||||
|
||||
@itemize
|
||||
@item
|
||||
@code{integer} - a C integral type; sb-grovel will infer the exact
|
||||
type from size information extracted from the C program. All common C
|
||||
integer types can be grovelled for with this type designator, but it
|
||||
is not possible to grovel for bit fields yet.
|
||||
@item @code{integer}: a C integral type; sb-grovel will infer the exact
|
||||
type from size information extracted from the C program. All
|
||||
common C integer types can be grovelled for with this type
|
||||
designator, but it is not possible to grovel for bit fields
|
||||
yet.
|
||||
|
||||
@item
|
||||
@code{(unsigned n)} - an unsigned integer variable that is @code{n}
|
||||
bytes long. No size information from the C program will be used.
|
||||
@item
|
||||
@code{(signed n)} - an signed integer variable that is @code{n} bytes
|
||||
long. No size information from the C program will be used.
|
||||
@item @code{(unsigned n)}: an unsigned integer variable that is @code{n} bytes
|
||||
long. No size information from the C program will be used.
|
||||
|
||||
@item
|
||||
@code{c-string} - an array of @code{char} in the structure. sb-grovel
|
||||
will use the array's length from the C program, unless you pass it the
|
||||
@code{:distrust-length} keyword argument with non-@code{nil} value
|
||||
(this might be required for structures such as solaris's @code{struct
|
||||
dirent}).
|
||||
@item @code{(signed n)}: an signed integer variable that is @code{n} bytes
|
||||
long. No size information from the C program will be used.
|
||||
|
||||
@item
|
||||
@code{c-string-pointer} - a pointer to a C string, corresponding to
|
||||
the @code{sb-alien:c-string} type (@pxref{Foreign Type Specifiers}).
|
||||
@item
|
||||
@code{(array alien-type)} - An array of the previously-declared alien
|
||||
type. The array's size will be determined from the output of the C
|
||||
program and the alien type's size.
|
||||
@item
|
||||
@code{(array alien-type n)} - An array of the previously-declared alien
|
||||
type. The array's size will be assumed as being @code{n}.
|
||||
@item @code{c-string}: an array of @code{char} in the structure. sb-grovel
|
||||
will use the array's length from the C program, unless you
|
||||
pass it the @code{:distrust-length} keyword argument with non-@code{nil}
|
||||
value (this might be required for structures such as solaris's
|
||||
@code{struct dirent}).
|
||||
|
||||
@item @code{sb-grovel::c-string-pointer}: a pointer to a C string,
|
||||
corresponding to the @code{sb-alien:c-string} type (see
|
||||
@ref{foreign type specifiers}).
|
||||
|
||||
@item @code{(array alien-type)}: an array of the previously-declared
|
||||
@code{alien-type}. The array's size will be determined from the
|
||||
output of the C program and the alien type's size.
|
||||
|
||||
@item @code{(array alien-type n):} an array of the previously-declared
|
||||
@code{alien-type}. The array's size will be assumed as being @code{n}.
|
||||
@end itemize
|
||||
@end itemize
|
||||
|
||||
|
||||
Note that @code{c-string} and @code{c-string-pointer} do not have the
|
||||
same meaning. If you declare that an element is of type
|
||||
Note that @code{c-string} and @code{sb-grovel::c-string-pointer} do not have
|
||||
the same meaning. If you declare that an element is of type
|
||||
@code{c-string}, it will be treated as if the string is a part of the
|
||||
structure, whereas if you declare that the element is of type
|
||||
@code{c-string-pointer}, a @emph{pointer to a string} will be the
|
||||
@code{sb-grovel::c-string-pointer}, a @emph{pointer to a string} will be the
|
||||
structure member.
|
||||
|
||||
@item
|
||||
@code{:function} - alien function definitions are similar to
|
||||
@code{define-alien-routine} definitions, because they expand to such
|
||||
forms when the lisp program is loaded. @xref{Foreign Function Calls}.
|
||||
@itemize
|
||||
@item @code{:function}: alien function definitions are similar to
|
||||
@code{define-alien-routine} definitions, because they expand to such
|
||||
forms when the lisp program is loaded. See
|
||||
@ref{foreign function calls}.
|
||||
|
||||
@lisp
|
||||
(:function lisp-function-name ("alien_function_name" alien-return-type
|
||||
@example
|
||||
(:function lisp-function-name
|
||||
("alien_function_name" alien-return-type
|
||||
(argument alien-type)
|
||||
(argument2 alien-type)))
|
||||
@end lisp
|
||||
@end example
|
||||
@end itemize
|
||||
|
||||
|
||||
@node sb grovel structures
|
||||
@subsection Programming with sb-grovel's structure types
|
||||
|
||||
Let us assume that you have a grovelled structure definition:
|
||||
@lisp
|
||||
(:structure mystruct ("struct my_structure"
|
||||
|
||||
@example
|
||||
(:structure mystruct ("struct my_structure"
|
||||
(integer myint "int" "st_int")
|
||||
(c-string mystring "char[]" "st_str")))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
What can you do with it? Here's a short interface document:
|
||||
|
||||
@itemize
|
||||
@item
|
||||
Creating and destroying objects:
|
||||
@item Creating and destroying objects:
|
||||
|
||||
@itemize
|
||||
@item
|
||||
Function @code{(allocate-mystruct)} - allocates an object of type @code{mystruct}and
|
||||
returns a system area pointer to it.
|
||||
@item
|
||||
Macro @code{(with-mystruct var ((member init) [...]) &body body)} -
|
||||
allocates an object of type @code{mystruct} that is valid in
|
||||
@var{body}. If @var{body} terminates or control unwinds out of
|
||||
@var{body}, the object pointed to by @var{var} will be deallocated.
|
||||
@item Function @code{(allocate-mystruct)} allocates an object of type
|
||||
@code{mystruct} and returns a system area pointer to it.
|
||||
|
||||
@item Macro @code{(with-mystruct var ((member init) [...]) &body body)}
|
||||
allocates an object of type @code{mystruct} that is valid in
|
||||
@code{body}. If @code{body} terminates or performs an non-local exit,
|
||||
the object pointed to by @code{var} will be deallocated.
|
||||
@end itemize
|
||||
|
||||
@item
|
||||
Accessing structure members:
|
||||
@item Accessing structure members:
|
||||
|
||||
@itemize
|
||||
@item
|
||||
@code{(mystruct-myint var)} and @code{(mystruct-mystring var)} return
|
||||
the value of the respective fields in @code{mystruct}.
|
||||
@item
|
||||
@code{(setf (mystruct-myint var) new-val)} and
|
||||
@code{(setf (mystruct-mystring var) new-val)} sets the value of the respective
|
||||
structure member to the value of @var{new-val}. Notice that in
|
||||
@code{(setf (mystruct-mystring var) new-val)}'s case, new-val is a lisp
|
||||
string.
|
||||
@item @code{(mystruct-myint var)} and @code{(mystruct-mystring var)} return
|
||||
the value of the respective fields in @code{mystruct}.
|
||||
|
||||
@item @code{(setf (mystruct-myint var) new-val)} and
|
||||
@code{(setf (mystruct-mystring var) new-val)} sets the value of the
|
||||
respective structure member to the value of @code{new-val}. Notice
|
||||
that in @code{(setf (mystruct-mystring var) new-val)}'s case,
|
||||
@code{new-val} is a lisp string.
|
||||
@end itemize
|
||||
@end itemize
|
||||
|
||||
@subsubsection Traps and Pitfalls
|
||||
@node sb grovel traps
|
||||
@subsection Traps and Pitfalls
|
||||
|
||||
Basically, you can treat functions and data structure definitions that
|
||||
sb-grovel spits out as if they were alien routines and types. This has
|
||||
a few implications that might not be immediately obvious (especially
|
||||
|
|
@ -239,13 +247,12 @@ if you have programmed in a previous version of sb-grovel that didn't
|
|||
use alien types):
|
||||
|
||||
@itemize
|
||||
@item
|
||||
You must take care of grovel-allocated structures yourself. They are
|
||||
alien types, so the garbage collector will not collect them when you
|
||||
drop the last reference.
|
||||
@item You must take care of grovel-allocated structures yourself. They
|
||||
are alien types, so the garbage collector will not collect them
|
||||
when you drop the last reference.
|
||||
|
||||
@item
|
||||
If you use the @code{with-mystruct} macro, be sure that no references
|
||||
to the variable thus allocated leaks out. It will be deallocated when
|
||||
the block exits.
|
||||
@item If you use the @code{with-mystruct} macro, be sure that no references
|
||||
to the variable thus allocated leaks out. It will be deallocated
|
||||
when the block exits.
|
||||
@end itemize
|
||||
|
||||
|
|
|
|||
|
|
@ -1,61 +1,363 @@
|
|||
@node sb-introspect
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node sb introspect
|
||||
@section sb-introspect
|
||||
@cindex Introspection Library
|
||||
|
||||
@menu
|
||||
* Finding Definitions: finding definitions.
|
||||
* Special Variables: sb introspect variables.
|
||||
* Functions: sb introspect functions.
|
||||
* Types and Classes: sb introspect types.
|
||||
* Allocation: sb introspect allocation.
|
||||
@end menu
|
||||
|
||||
The @code{sb-introspect} module is about finding definitions, as well
|
||||
as querying their properties and relationships in the running image.
|
||||
|
||||
@menu
|
||||
* Finding Definitions::
|
||||
* Special Variables in sb-introspect::
|
||||
* Functions::
|
||||
* Types and Classes::
|
||||
* Allocation::
|
||||
@end menu
|
||||
|
||||
|
||||
@node Finding Definitions
|
||||
@node finding definitions
|
||||
@subsection Finding Definitions
|
||||
|
||||
@include struct-sb-introspect-definition-source.texinfo
|
||||
@include fun-sb-introspect-definition-source-pathname.texinfo
|
||||
@include fun-sb-introspect-definition-source-form-path.texinfo
|
||||
@include fun-sb-introspect-definition-source-form-number.texinfo
|
||||
@include fun-sb-introspect-definition-source-character-offset.texinfo
|
||||
@include fun-sb-introspect-definition-source-file-write-date.texinfo
|
||||
@include fun-sb-introspect-definition-source-plist.texinfo
|
||||
@anchor{Structure sb-introspect definition-source}
|
||||
@ttindex @sortas{definition-source sb-introspect} definition-source [sb-introspect]
|
||||
@deffn{Structure} sb-introspect:definition-source
|
||||
This structure identifies a sexp in a compiled file.
|
||||
Despite the name, the source location may not correspond to a
|
||||
definition but to e.g. a function call (see @code{who-calls}).
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect definition-source-pathname}
|
||||
@ffindex @sortas{definition-source-pathname sb-introspect} definition-source-pathname [sb-introspect]
|
||||
@deffn{Function} sb-introspect:definition-source-pathname instance
|
||||
Pathname of the source file.
|
||||
This is @code{nil} if the source location is not in a compiled file.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect definition-source-form-path}
|
||||
@ffindex @sortas{definition-source-form-path sb-introspect} definition-source-form-path [sb-introspect]
|
||||
@deffn{Function} sb-introspect:definition-source-form-path instance
|
||||
List of indices that identify the sexp in the
|
||||
file given by @code{definition-source-pathname}. The first element in the
|
||||
list is the index of the top-level form that contains the sexp. If the
|
||||
file was compiled at a high enough debug level, then the rest of the
|
||||
elements recursively index into the list structure of the top-level
|
||||
form.
|
||||
|
||||
@include fun-sb-introspect-find-definition-source.texinfo
|
||||
@include fun-sb-introspect-find-definition-sources-by-name.texinfo
|
||||
Thus, the form path is somewhat stable regarding edits in the file,
|
||||
but it gets invalidated by, for example, inserting a new top-level
|
||||
form before the sexp in question.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect definition-source-form-number}
|
||||
@ffindex @sortas{definition-source-form-number sb-introspect} definition-source-form-number [sb-introspect]
|
||||
@deffn{Function} sb-introspect:definition-source-form-number instance
|
||||
Depth-first index of the sexp within the top-level
|
||||
form identified by the first element of @code{definition-source-form-path}.
|
||||
That is, this is the index of the sexp in the list of subexpressions
|
||||
of the top-level form ordered according to depth-first traversal. 0
|
||||
corresponds to the top-level form itself.
|
||||
|
||||
@node Special Variables in sb-introspect
|
||||
When combined with the index of the top-level form (given by the first
|
||||
element of @code{definition-source-form-path}), the form number allows
|
||||
reconstruction of the rest of the form path, which may be missing.
|
||||
This requires parsing the source file. Currently, this job is
|
||||
delegated to e.g. SLIME.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect definition-source-character-offset}
|
||||
@ffindex @sortas{definition-source-character-offset sb-introspect} definition-source-character-offset [sb-introspect]
|
||||
@deffn{Function} sb-introspect:definition-source-character-offset instance
|
||||
Character offset of the top-level form containing
|
||||
the sexp.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect definition-source-file-write-date}
|
||||
@ffindex @sortas{definition-source-file-write-date sb-introspect} definition-source-file-write-date [sb-introspect]
|
||||
@deffn{Function} sb-introspect:definition-source-file-write-date instance
|
||||
@code{file-write-date} of @code{definition-source-pathname} at
|
||||
the time of compilation. @code{nil} if not compiled from a file.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect definition-source-plist}
|
||||
@ffindex @sortas{definition-source-plist sb-introspect} definition-source-plist [sb-introspect]
|
||||
@deffn{Function} sb-introspect:definition-source-plist instance
|
||||
The @code{source-plist} from @code{with-compilation-unit} in effect
|
||||
when the file was compiled.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect find-definition-source}
|
||||
@ffindex @sortas{find-definition-source sb-introspect} find-definition-source [sb-introspect]
|
||||
@deffn{Function} sb-introspect:find-definition-source object
|
||||
Return the @code{definition-source} corresponding to the definition of @code{object}
|
||||
or @code{nil} if there is no corresponding definition. @code{object} must be a
|
||||
@code{package}, @code{function}, @code{method}, @code{method-combination}, @code{sb-mop:slot-definition},
|
||||
@code{standard-object}, @code{structure-object}, @code{condition}, @code{class}, @code{structure-class},
|
||||
or a subclass of @code{condition}. An error is signalled for other types.
|
||||
|
||||
A @code{definition-source} object is always returned for definitions that
|
||||
exist, but the source location (e.g. @code{definition-source-pathname}) may
|
||||
be missing.
|
||||
|
||||
For definitions that do not define an object (e.g. @code{defvar}), use
|
||||
@code{find-definition-sources-by-name}.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect find-definition-sources-by-name}
|
||||
@ffindex @sortas{find-definition-sources-by-name sb-introspect} find-definition-sources-by-name [sb-introspect]
|
||||
@deffn{Function} sb-introspect:find-definition-sources-by-name name type
|
||||
Returns a list of @code{definition-source}s for definitions of @code{name} with
|
||||
the given definition @code{type}. A @code{definition-source} object is always
|
||||
returned for definitions that exist, but the source location (e.g.
|
||||
@code{definition-source-pathname}) may be missing. @code{type} can currently be one
|
||||
of the following.
|
||||
|
||||
@itemize
|
||||
@item Public definition types:
|
||||
|
||||
@code{:class}
|
||||
@code{:compiler-macro}
|
||||
@code{:condition}
|
||||
@code{:constant}
|
||||
@code{:function}
|
||||
@code{:generic-function}
|
||||
@code{:macro}
|
||||
@code{:method}
|
||||
@code{:method-combination}
|
||||
@code{:package}
|
||||
@code{:setf-expander}
|
||||
@code{:structure}
|
||||
@code{:symbol-macro}
|
||||
@code{:type}
|
||||
@code{:alien-type}
|
||||
@code{:alien-callback}
|
||||
@code{:variable}
|
||||
@code{:declaration}
|
||||
|
||||
@item Internal definition types:
|
||||
|
||||
@code{:optimizer}
|
||||
@code{:source-transform}
|
||||
@code{:transform}
|
||||
@code{:vop}
|
||||
@code{:ir1-convert}
|
||||
@end itemize
|
||||
|
||||
Definition types are disjoint. For example, @code{:type} refers to @code{deftype}s
|
||||
but not @code{class}es or @code{sb-alien:define-alien-type}, as those are of
|
||||
definition type @code{:class} and @code{:alien-type}, respectively. @code{:function} does
|
||||
not include @code{:generic-function}, @code{:class} does not include @code{:structure},
|
||||
etc. @code{:variable} refers to non-constant dynamic variables (e.g. those
|
||||
defined with @code{defvar}, @code{defparameter}, @code{sb-ext:defglobal} or
|
||||
@code{sb-alien:define-alien-variable} but not with @code{defconstant}).
|
||||
|
||||
Valid @code{name}s are generally @code{symbol}s with the following exceptions:
|
||||
|
||||
@itemize
|
||||
@item For @code{:compiler-macro}, @code{:function}, @code{:generic-function} and @code{:method},
|
||||
anything that's @code{valid-function-name-p} is valid.
|
||||
|
||||
@item For @code{:package}, string designators are valid.
|
||||
@end itemize
|
||||
|
||||
If an unsupported @code{type} is requested or @code{name} is invalid, this function
|
||||
returns @code{nil}.
|
||||
@end deffn
|
||||
@node sb introspect variables
|
||||
@subsection Special Variables
|
||||
|
||||
@include fun-sb-introspect-who-binds.texinfo
|
||||
@include fun-sb-introspect-who-references.texinfo
|
||||
@include fun-sb-introspect-who-sets.texinfo
|
||||
|
||||
@node Functions
|
||||
@anchor{Function sb-introspect who-binds}
|
||||
@ffindex @sortas{who-binds sb-introspect} who-binds [sb-introspect]
|
||||
@deffn{Function} sb-introspect:who-binds symbol
|
||||
Find the source locations where the special variable @code{symbol} is bound,
|
||||
and return them as an alist of function or macro name,
|
||||
@code{definition-source} pairs.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect who-references}
|
||||
@ffindex @sortas{who-references sb-introspect} who-references [sb-introspect]
|
||||
@deffn{Function} sb-introspect:who-references symbol
|
||||
Find the source locations where the special variable @code{symbol} is read,
|
||||
and return them as an alist of function or macro name,
|
||||
@code{definition-source} pairs.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect who-sets}
|
||||
@ffindex @sortas{who-sets sb-introspect} who-sets [sb-introspect]
|
||||
@deffn{Function} sb-introspect:who-sets symbol
|
||||
Find the source locations where the special variable @code{symbol} is set,
|
||||
and return them as an alist of function or macro name,
|
||||
@code{definition-source} pairs.
|
||||
@end deffn
|
||||
@node sb introspect functions
|
||||
@subsection Functions
|
||||
|
||||
@include fun-sb-introspect-function-lambda-list.texinfo
|
||||
@include fun-sb-introspect-function-type.texinfo
|
||||
@include fun-sb-introspect-method-combination-lambda-list.texinfo
|
||||
@include fun-sb-introspect-valid-function-name-p.texinfo
|
||||
@include fun-sb-introspect-find-function-callers.texinfo
|
||||
@include fun-sb-introspect-find-function-callees.texinfo
|
||||
@include fun-sb-introspect-who-calls.texinfo
|
||||
@include fun-sb-introspect-who-macroexpands.texinfo
|
||||
@anchor{Function sb-introspect function-lambda-list}
|
||||
@ffindex @sortas{function-lambda-list sb-introspect} function-lambda-list [sb-introspect]
|
||||
@deffn{Function} sb-introspect:function-lambda-list function
|
||||
Return the lambda list of @code{function}.
|
||||
@code{function} must be a function object or a function name in the sense of
|
||||
@code{valid-function-name-p}. Works for special operators, macros, simple
|
||||
functions, interpreted functions, and generic functions.
|
||||
|
||||
@node Types and Classes
|
||||
The second return value indicates whether the lambda list could not be
|
||||
determined (e.g. because the function was compiled with @code{debug} 0).
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect function-type}
|
||||
@ffindex @sortas{function-type sb-introspect} function-type [sb-introspect]
|
||||
@deffn{Function} sb-introspect:function-type function-designator
|
||||
Returns the ftype of @code{function-designator} or @code{nil}.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect method-combination-lambda-list}
|
||||
@ffindex @sortas{method-combination-lambda-list sb-introspect} method-combination-lambda-list [sb-introspect]
|
||||
@deffn{Function} sb-introspect:method-combination-lambda-list method-combination
|
||||
Return the lambda list of the @code{method-combination} designator.
|
||||
@code{method-combination} can be a method combination object,
|
||||
or a method combination name.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect valid-function-name-p}
|
||||
@ffindex @sortas{valid-function-name-p sb-introspect} valid-function-name-p [sb-introspect]
|
||||
@deffn{Function} sb-introspect:valid-function-name-p name
|
||||
See if @code{name} is a valid function name. In addition to the ANSI
|
||||
definition of function name, which is symbols plus lists like (@code{setf}
|
||||
@code{symbol}), SBCL allows (@code{sb-ext:cas} @code{symbol}) and various internal
|
||||
constructs.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect find-function-callers}
|
||||
@ffindex @sortas{find-function-callers sb-introspect} find-function-callers [sb-introspect]
|
||||
@deffn{Function} sb-introspect:find-function-callers function &optional spaces
|
||||
List functions that call @code{function} by searching @code{spaces} for code objects.
|
||||
This can make previously garbage objects live.
|
||||
|
||||
@code{spaces} should be a list of the symbols @code{:dynamic}, @code{:static}, @code{:read-only},
|
||||
or @code{:immobile} on @code{#+immobile-space}. The shorthand (@code{:all}) is also
|
||||
accepted.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect find-function-callees}
|
||||
@ffindex @sortas{find-function-callees sb-introspect} find-function-callees [sb-introspect]
|
||||
@deffn{Function} sb-introspect:find-function-callees function
|
||||
Return functions called by @code{function}.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect who-calls}
|
||||
@ffindex @sortas{who-calls sb-introspect} who-calls [sb-introspect]
|
||||
@deffn{Function} sb-introspect:who-calls function-name
|
||||
Find the source locations where the global function @code{function-name} is
|
||||
called, and return them as an alist of function or macro name,
|
||||
@code{definition-source} pairs.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect who-macroexpands}
|
||||
@ffindex @sortas{who-macroexpands sb-introspect} who-macroexpands [sb-introspect]
|
||||
@deffn{Function} sb-introspect:who-macroexpands macro-name
|
||||
Find the source locations where the macro @code{macro-name} is expanded, and
|
||||
return them as an alist of function or macro name, @code{definition-source}
|
||||
pairs.
|
||||
@end deffn
|
||||
@node sb introspect types
|
||||
@subsection Types and Classes
|
||||
|
||||
@include fun-sb-introspect-deftype-lambda-list.texinfo
|
||||
@include fun-sb-introspect-who-specializes-directly.texinfo
|
||||
@include fun-sb-introspect-who-specializes-generally.texinfo
|
||||
@anchor{Function sb-introspect deftype-lambda-list}
|
||||
@ffindex @sortas{deftype-lambda-list sb-introspect} deftype-lambda-list [sb-introspect]
|
||||
@deffn{Function} sb-introspect:deftype-lambda-list type-specifier-name
|
||||
Returns the lambda list of @code{type-specifier-name} as the first return
|
||||
value, and a flag whether the arglist could be found as the second
|
||||
value.
|
||||
|
||||
@node Allocation
|
||||
@code{type-specifier-name} must be a symbol. This function can find the
|
||||
lambda list of derived type specifiers (e.g. those defined with
|
||||
@code{deftype}) and classes with compound type specifier syntaxes (e.g. the
|
||||
class @code{float}). It returns @code{nil}, @code{nil} for other type specifiers (e.g. @code{and},
|
||||
@code{or}, @code{not}) and types (e.g. @code{list}).
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect who-specializes-directly}
|
||||
@ffindex @sortas{who-specializes-directly sb-introspect} who-specializes-directly [sb-introspect]
|
||||
@deffn{Function} sb-introspect:who-specializes-directly class-designator
|
||||
Find the source locations of methods directly specializing on
|
||||
@code{class-designator}, and return them as an alist of generic function
|
||||
name, @code{definition-source} pairs.
|
||||
|
||||
A method matches the criterion either if it specializes on the same
|
||||
class as @code{class-designator} designates, or if it eql-specializes on an
|
||||
instance of the designated class.
|
||||
|
||||
Experimental.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect who-specializes-generally}
|
||||
@ffindex @sortas{who-specializes-generally sb-introspect} who-specializes-generally [sb-introspect]
|
||||
@deffn{Function} sb-introspect:who-specializes-generally class-designator
|
||||
Find the source locations of methods specializing on
|
||||
@code{class-designator} or a subclass of it, and return them as an alist of
|
||||
generic function name, @code{definition-source} pairs.
|
||||
@code{definition-source-description} identifies the method.
|
||||
|
||||
A method matches the criterion either if it specializes on the
|
||||
designated class itself or a subclass of it (this includes CLASS-EQ
|
||||
specializers), or if it eql-specializes on an instance of the
|
||||
designated class or a subclass of it.
|
||||
|
||||
Experimental.
|
||||
@end deffn
|
||||
@node sb introspect allocation
|
||||
@subsection Allocation
|
||||
|
||||
@include fun-sb-introspect-allocation-information.texinfo
|
||||
@include fun-sb-introspect-map-root.texinfo
|
||||
@anchor{Function sb-introspect allocation-information}
|
||||
@ffindex @sortas{allocation-information sb-introspect} allocation-information [sb-introspect]
|
||||
@deffn{Function} sb-introspect:allocation-information object
|
||||
Returns information about the allocation of @code{object}. The primary return
|
||||
value indicates the general type of allocation: @code{:immediate}, @code{:heap},
|
||||
@code{:stack}, or @code{:foreign}.
|
||||
|
||||
Non-NIL secondary return values provide additional information about
|
||||
the allocation.
|
||||
|
||||
For @code{:heap} objects the secondary value is a plist:
|
||||
|
||||
@code{:space}
|
||||
Indicates the heap segment the object is allocated in.
|
||||
|
||||
@code{:generation}
|
||||
The current generation of the object: 0 for nursery, 6 for pseudo-static
|
||||
generation loaded from core. (GENCGC and @code{:space} @code{:dynamic} only.)
|
||||
|
||||
@code{:large}
|
||||
Indicates a "large" object subject to non-copying
|
||||
promotion. (GENCGC and @code{:space} @code{:dynamic} only.)
|
||||
|
||||
@code{:boxed}
|
||||
Indicates that the object is allocated in a boxed region. Unboxed
|
||||
allocation is used for e.g. specialized arrays after they have survived one
|
||||
collection. (GENCGC and @code{:space} @code{:dynamic} only.)
|
||||
|
||||
@code{:pinned}
|
||||
Indicates that the page(s) on which the object resides are kept live due
|
||||
to conservative references. Note that object may reside on a pinned page
|
||||
even if @code{:pinned} is @code{nil} if the GC has not had the need to mark the page
|
||||
as pinned. (GENCGC and @code{:space} @code{:dynamic} only.)
|
||||
|
||||
@code{:write-protected}
|
||||
Indicates that the page on which the object starts is write-protected,
|
||||
which indicates for @code{:boxed} objects that it hasn't been written to since
|
||||
the last GC of its generation. (GENCGC and @code{:space} @code{:dynamic} only.)
|
||||
|
||||
@code{:page}
|
||||
The index of the page the object resides on. (GENCGC and @code{:space} @code{:dynamic}
|
||||
only.)
|
||||
|
||||
For @code{:stack} objects, the secondary value is the thread on whose stack
|
||||
the object is allocated.
|
||||
|
||||
Expected use-cases include introspection to gain insight into allocation and
|
||||
GC behaviour and restricting memoization to heap-allocated arguments.
|
||||
|
||||
Experimental: interface subject to change.
|
||||
@end deffn
|
||||
@anchor{Function sb-introspect map-root}
|
||||
@ffindex @sortas{map-root sb-introspect} map-root [sb-introspect]
|
||||
@deffn{Function} sb-introspect:map-root function object &key simple ext
|
||||
Call @code{function} with all non-immediate objects pointed to by @code{object}.
|
||||
Returns @code{object}.
|
||||
|
||||
If @code{simple} is true (default is @code{nil}), elides those pointers that are not
|
||||
notionally part of certain built-in objects but backpointers to a
|
||||
conceptual parent: e.g. elides the pointer from a @code{symbol} to the
|
||||
corresponding @code{package}.
|
||||
|
||||
If @code{ext} is true (default is @code{t}), includes some pointers that are not
|
||||
actually contained in the object but found in certain well-known
|
||||
indirect containers: @code{fdefinition}s, @code{eql} specializers, classes, and
|
||||
thread-local symbol values in other threads fall into this category.
|
||||
|
||||
@quotation
|
||||
@emph{Note}: calling @code{map-root} with a THREAD does not currently map over
|
||||
conservative roots from the thread registers and interrupt contexts.
|
||||
@end quotation
|
||||
|
||||
Experimental: interface subject to change.
|
||||
@end deffn
|
||||
|
|
|
|||
|
|
@ -1,27 +1,48 @@
|
|||
@node sb-md5
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node sb md5
|
||||
@section sb-md5
|
||||
@cindex Hashing, cryptographic
|
||||
|
||||
The @code{sb-md5} module implements the RFC1321 MD5 Message Digest
|
||||
Algorithm. [FIXME cite]
|
||||
|
||||
@include fun-sb-md5-md5sum-file.texinfo
|
||||
|
||||
@include fun-sb-md5-md5sum-sequence.texinfo
|
||||
|
||||
@include fun-sb-md5-md5sum-stream.texinfo
|
||||
|
||||
@include fun-sb-md5-md5sum-string.texinfo
|
||||
|
||||
@subsection Credits
|
||||
Algorithm.
|
||||
|
||||
@anchor{Function sb-md5 md5sum-file}
|
||||
@ffindex @sortas{md5sum-file sb-md5} md5sum-file [sb-md5]
|
||||
@deffn{Function} sb-md5:md5sum-file pathname
|
||||
Calculate the MD5 message-digest of the file specified by @code{pathname}.
|
||||
@end deffn
|
||||
@anchor{Function sb-md5 md5sum-sequence}
|
||||
@ffindex @sortas{md5sum-sequence sb-md5} md5sum-sequence [sb-md5]
|
||||
@deffn{Function} sb-md5:md5sum-sequence sequence &key start end
|
||||
Calculate the MD5 message-digest of data in @code{sequence}, which should
|
||||
be a 1d @code{simple-array} with element type (@code{unsigned-byte} 8). On CMU CL
|
||||
and SBCL non-simple and non-1d arrays with this element-type are also
|
||||
supported.
|
||||
@end deffn
|
||||
@anchor{Function sb-md5 md5sum-stream}
|
||||
@ffindex @sortas{md5sum-stream sb-md5} md5sum-stream [sb-md5]
|
||||
@deffn{Function} sb-md5:md5sum-stream stream
|
||||
Calculate an MD5 message-digest of the contents of @code{stream}. Its
|
||||
element-type has to be (@code{unsigned-byte} 8). Use on character streams is
|
||||
DEPRECATED, as this will not work correctly on implementations with
|
||||
@code{char-code-limit} > 256 and ignores character coding issues.
|
||||
@end deffn
|
||||
@anchor{Function sb-md5 md5sum-string}
|
||||
@ffindex @sortas{md5sum-string sb-md5} md5sum-string [sb-md5]
|
||||
@deffn{Function} sb-md5:md5sum-string string &key external-format start end
|
||||
Calculate the MD5 message-digest of the binary representation of
|
||||
@code{string} (as octets) in the external format specified by
|
||||
@code{external-format}. The boundaries @code{start} and @code{end} refer to character
|
||||
positions in the string, not to octets in the resulting binary
|
||||
representation. The permissible external format specifiers are
|
||||
determined by the underlying implementation.
|
||||
@end deffn
|
||||
The implementation for CMUCL was largely done by Pierre Mai, with help
|
||||
from members of the @code{cmucl-help} mailing list. Since CMUCL and
|
||||
SBCL are similar in many respects, it was not too difficult to extend
|
||||
the low-level implementation optimizations for CMUCL to SBCL.
|
||||
Following this, SBCL's compiler was extended to implement efficient
|
||||
compilation of modular arithmetic (@pxref{Modular arithmetic}), which
|
||||
from members of the @code{cmucl-help} mailing list. Since CMUCL and SBCL
|
||||
are similar in many respects, it was not too difficult to extend the
|
||||
low-level implementation optimizations for CMUCL to SBCL. Following
|
||||
this, SBCL's compiler was extended to implement efficient
|
||||
compilation of modular arithmetic (@ref{modular arithmetic}), which
|
||||
enabled the implementation to be expressed in portable arithmetical
|
||||
terms, apart from the use of @code{rotate-byte} for bitwise rotation.
|
||||
@findex @sbrotatebyte{rotate-byte}
|
||||
terms, apart from the use of @ref{sb rotate byte} for bitwise rotation.
|
||||
|
||||
|
|
|
|||
|
|
@ -1,151 +1,206 @@
|
|||
@node sb-posix
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node sb posix
|
||||
@section sb-posix
|
||||
@cindex Operating System Interface
|
||||
@cindex System Calls
|
||||
@cindex Posix
|
||||
|
||||
Sb-posix is the supported interface for calling out to the operating
|
||||
system.@footnote{The functionality contained in the package
|
||||
@code{SB-UNIX} is for SBCL internal use only; its contents are likely to
|
||||
change from version to version.}
|
||||
|
||||
The scope of this interface is ``operating system calls on a typical
|
||||
Unixlike platform''. This is section 2 of the Unix manual, plus section
|
||||
3 calls that are (a) typically found in libc, but (b) not part of the C
|
||||
standard. For example, we intend to provide support for
|
||||
@code{opendir()} and @code{readdir()}, but not for @code{printf()}.
|
||||
That said, if your favourite system call is not included yet, you are
|
||||
encouraged to submit a patch to the SBCL mailing list.
|
||||
|
||||
Some facilities are omitted where they offer absolutely no additional
|
||||
use over some portable function, or would be actively dangerous to the
|
||||
consistency of Lisp. Not all functions are available on all
|
||||
platforms.
|
||||
|
||||
Sb-posix functions do not implicitly take measures to provide thread-safety
|
||||
or reentrancy beyond whatever the underlying C library does, except in
|
||||
cases where doing so is necessary to maintain the consistency of the
|
||||
Lisp image. For example, the bindings to the user and group database
|
||||
accessing functions are neither thread-safe nor reentrant unless the
|
||||
underlying libc happens to make them so (but @pxref{Extensions to
|
||||
POSIX}).
|
||||
|
||||
@menu
|
||||
* Lisp names for C names::
|
||||
* Types::
|
||||
* Function Parameters::
|
||||
* Function Return Values::
|
||||
* Lisp objects and C structures::
|
||||
* Functions with idiosyncratic bindings::
|
||||
* Extensions to POSIX::
|
||||
* Lisp names for C names: sb posix lisp names.
|
||||
* Types: sb posix types.
|
||||
* Function Parameters: sb posix function parameters.
|
||||
* Function Return Values: sb posix function return values.
|
||||
* Lisp Objects and C structures: sb posix lisp objects and c structures.
|
||||
* Functions with Idiosyncratic Bindings: sb posix idiosyncracies.
|
||||
* Extensions to POSIX: sb posix extensions to posix.
|
||||
@end menu
|
||||
|
||||
Sb-posix is the supported interface for calling out to the operating
|
||||
system.
|
||||
|
||||
@node Lisp names for C names
|
||||
@quotation
|
||||
@emph{Note}: The functionality contained in the package @code{sb-unix} is
|
||||
for SBCL internal use only; its contents are likely to change from
|
||||
version to version.
|
||||
@end quotation
|
||||
|
||||
The scope of this interface is "operating system calls on a typical
|
||||
Unixlike platform". This is section 2 of the Unix manual, plus
|
||||
section 3 calls that are (a) typically found in libc, but (b) not
|
||||
part of the C standard. For example, we intend to provide support
|
||||
for @code{opendir(3)} and @code{readdir(3)} but not for @code{printf(3)}. That
|
||||
said, if your favourite system call is not included yet, you are
|
||||
encouraged to submit a patch to the SBCL mailing list.
|
||||
|
||||
Some facilities are omitted where they offer absolutely no
|
||||
additional use over some portable function, or would be actively
|
||||
dangerous to the consistency of Lisp. Not all functions are
|
||||
available on all platforms.
|
||||
|
||||
Sb-posix functions do not implicitly take measures to provide
|
||||
thread-safety or reentrancy beyond whatever the underlying C library
|
||||
does, except in cases where doing so is necessary to maintain the
|
||||
consistency of the Lisp image. For example, the bindings to the user
|
||||
and group database accessing functions are neither thread-safe nor
|
||||
reentrant unless the underlying libc happens to make them so (but
|
||||
see @ref{sb posix extensions to posix}).
|
||||
|
||||
@node sb posix lisp names
|
||||
@subsection Lisp names for C names
|
||||
|
||||
All symbols are in the @code{SB-POSIX} package. This package contains a
|
||||
All symbols are in the @code{sb-posix} package. This package contains a
|
||||
Lisp function for each supported Unix system call or function, a
|
||||
variable or constant for each supported Unix constant, an object type
|
||||
for each supported Unix structure type, and a slot name for each
|
||||
supported Unix structure member. A symbol name is derived from the C
|
||||
binding's name, by (a) uppercasing, then (b) removing leading
|
||||
variable or constant for each supported Unix constant, an object
|
||||
type for each supported Unix structure type, and a slot name for
|
||||
each supported Unix structure member. A symbol name is derived from
|
||||
the C binding's name, by (a) uppercasing, then (b) removing leading
|
||||
underscores (@code{#\_}) then replacing remaining underscore characters
|
||||
with the hyphen (@code{#\-}). The requirement to uppercase is so that in
|
||||
a standard upcasing reader the user may write @code{sb-posix:creat}
|
||||
instead of @code{sb-posix:|creat|} as would otherise be required.
|
||||
|
||||
No other changes to ``Lispify'' symbol names are made, so @code{creat()}
|
||||
becomes @code{CREAT}, not @code{CREATE}.
|
||||
No other changes to "Lispify" symbol names are made, so
|
||||
@code{creat} becomes @code{CREAT}, not @code{CREATE}.
|
||||
|
||||
The user is encouraged not to @code{(USE-PACKAGE :SB-POSIX)} but instead
|
||||
to use the @code{SB-POSIX:} prefix on all references, as some of the
|
||||
symbols symbols contained in the SB-POSIX package have the same name as
|
||||
CL symbols (@code{OPEN}, @code{CLOSE}, @code{SIGNAL} etc).
|
||||
The user is encouraged not to @code{(use-package :sb-posix)} but instead
|
||||
to use the @code{sb-posix:} prefix on all references, as some of the
|
||||
symbols symbols contained in the @code{sb-posix} package have the same
|
||||
name as CL symbols (e.g. @code{open}, @code{close}, @code{signal}). Also, see
|
||||
@ref{package local nicknames}.
|
||||
|
||||
@node Types
|
||||
@node sb posix types
|
||||
@subsection Types
|
||||
|
||||
Generally, marshalling between Lisp and C data types is done using
|
||||
SBCL's FFI. @xref{Foreign Function Interface}.
|
||||
|
||||
Some functions accept objects such as filenames or file descriptors. In
|
||||
the C binding to POSIX these are represented as strings and small
|
||||
integers respectively. For the Lisp programmer's convenience we
|
||||
introduce designators such that CL pathnames or open streams can be
|
||||
passed to these functions. For example, @code{rename} accepts both
|
||||
pathnames and strings as its arguments.
|
||||
|
||||
@menu
|
||||
* File-descriptors::
|
||||
* Filenames::
|
||||
* File-descriptors: sb posix file descriptors.
|
||||
* Filenames: sb posix filenames.
|
||||
@end menu
|
||||
|
||||
@node File-descriptors
|
||||
Generally, marshalling between Lisp and C data types is done using
|
||||
SBCL's FFI. See @ref{foreign function interface}.
|
||||
|
||||
Some functions accept objects such as filenames or file descriptors.
|
||||
In the C binding to POSIX, these are represented as strings and
|
||||
small integers respectively. For the Lisp programmer's convenience
|
||||
we introduce designators such that CL pathnames or open streams can
|
||||
be passed to these functions. For example, @code{sb-posix:rename} accepts
|
||||
both pathnames and strings as its arguments.
|
||||
|
||||
@node sb posix file descriptors
|
||||
@subsubsection File-descriptors
|
||||
|
||||
@include type-sb-posix-file-descriptor.texinfo
|
||||
@include type-sb-posix-file-descriptor-designator.texinfo
|
||||
@include fun-sb-posix-file-descriptor.texinfo
|
||||
@anchor{Type sb-posix file-descriptor}
|
||||
@ttindex @sortas{file-descriptor sb-posix} file-descriptor [sb-posix]
|
||||
@deffn{Type} sb-posix:file-descriptor
|
||||
A @code{fixnum} designating a native file descriptor.
|
||||
|
||||
@node Filenames
|
||||
@code{sb-sys:make-fd-stream} can be used to construct a @code{file-stream} associated with a
|
||||
native file descriptor.
|
||||
|
||||
Note that mixing I/O operations on a @code{file-stream} with operations directly on its
|
||||
descriptor may produce unexpected results if the stream is buffered.
|
||||
@end deffn
|
||||
@anchor{Type sb-posix file-descriptor-designator}
|
||||
@ttindex @sortas{file-descriptor-designator sb-posix} file-descriptor-designator [sb-posix]
|
||||
@deffn{Type} sb-posix:file-descriptor-designator
|
||||
Designator for a @code{file-descriptor}: either a fixnum designating
|
||||
itself, or a @code{file-stream} designating the underlying file-descriptor.
|
||||
@end deffn
|
||||
@anchor{Function sb-posix file-descriptor}
|
||||
@ffindex @sortas{file-descriptor sb-posix} file-descriptor [sb-posix]
|
||||
@deffn{Function} sb-posix:file-descriptor file-descriptor
|
||||
Converts @code{file-descriptor-designator} into a @code{file-descriptor}.
|
||||
@end deffn
|
||||
@node sb posix filenames
|
||||
@subsubsection Filenames
|
||||
|
||||
@include type-sb-posix-filename.texinfo
|
||||
@include type-sb-posix-filename-designator.texinfo
|
||||
@include fun-sb-posix-filename.texinfo
|
||||
@anchor{Type sb-posix filename}
|
||||
@ttindex @sortas{filename sb-posix} filename [sb-posix]
|
||||
@deffn{Type} sb-posix:filename
|
||||
A @code{string} designating a filename in native namestring syntax.
|
||||
|
||||
@node Function Parameters
|
||||
Note that native namestring syntax is distinct from Lisp namestring syntax:
|
||||
|
||||
@example
|
||||
(pathname "/foo*/bar")
|
||||
@end example
|
||||
|
||||
is a wild pathname with a pattern-matching directory component.
|
||||
@code{sb-ext:parse-native-namestring} may be used to construct Lisp pathnames that
|
||||
denote POSIX filenames as understood by system calls, and
|
||||
@code{sb-ext:native-namestring} can be used to coerce them into strings in the native
|
||||
namestring syntax.
|
||||
|
||||
Note also that POSIX filename syntax does not distinguish the names of files
|
||||
from the names of directories: in order to parse the name of a directory in
|
||||
POSIX filename syntax into a pathname @code{my-defaults} for which
|
||||
|
||||
@example
|
||||
(merge-pathnames (make-pathname :name "FOO" :case :common)
|
||||
my-defaults)
|
||||
@end example
|
||||
|
||||
returns a pathname that denotes a file in the directory, supply a true
|
||||
@code{:as-directory} argument to @code{sb-ext:parse-native-namestring}. Likewise, to supply
|
||||
the name of a directory to a POSIX function in non-directory syntax, supply a
|
||||
true @code{:as-file} argument to @code{sb-ext:native-namestring}.
|
||||
@end deffn
|
||||
@anchor{Type sb-posix filename-designator}
|
||||
@ttindex @sortas{filename-designator sb-posix} filename-designator [sb-posix]
|
||||
@deffn{Type} sb-posix:filename-designator
|
||||
Designator for a @code{filename}: a @code{string} designating itself, or a
|
||||
designator for a @code{pathname} designating the corresponding native namestring.
|
||||
@end deffn
|
||||
@anchor{Function sb-posix filename}
|
||||
@ffindex @sortas{filename sb-posix} filename [sb-posix]
|
||||
@deffn{Function} sb-posix:filename filename
|
||||
Converts @code{filename-designator} into a @code{filename}.
|
||||
@end deffn
|
||||
@node sb posix function parameters
|
||||
@subsection Function Parameters
|
||||
|
||||
The calling convention is modelled after that of CMUCL's @code{UNIX}
|
||||
The calling convention is modelled after that of CMUCL's @code{unix}
|
||||
package: in particular, it's like the C interface except that:
|
||||
|
||||
@enumerate a
|
||||
@item
|
||||
Length arguments are omitted or optional where the sensible value
|
||||
is obvious. For example, @code{read} would be defined this way:
|
||||
@itemize
|
||||
@item Length arguments are omitted or optional where the sensible value
|
||||
is obvious. For example, @code{read} would be defined this way:
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(read fd buffer &optional (length (length buffer))) => bytes-read
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
@item
|
||||
Where C simulates ``out'' parameters using pointers (for instance, in
|
||||
@code{pipe()} or @code{socketpair()}) these may be optional or omitted
|
||||
in the Lisp interface: if not provided, appropriate objects will be
|
||||
allocated and returned (using multiple return values if necessary).
|
||||
@item Where C simulates "out" parameters using pointers (for instance,
|
||||
in @code{pipe(2)} or @code{socketpair(2)}), these may be optional or omitted
|
||||
in the Lisp interface: if not provided, appropriate objects will
|
||||
be allocated and returned (using multiple return values if
|
||||
necessary).
|
||||
|
||||
@item
|
||||
Some functions accept objects such as filenames or file descriptors.
|
||||
Wherever these are specified as such in the C bindings, the Lisp
|
||||
interface accepts designators for them as specified in the 'Types'
|
||||
section above.
|
||||
@item Some functions accept objects such as filenames or file
|
||||
descriptors. Wherever these are specified as such in the C
|
||||
bindings, the Lisp interface accepts designators for them as
|
||||
specified in the @ref{sb posix types} section above.
|
||||
|
||||
@item
|
||||
A few functions have been included in sb-posix that do not correspond
|
||||
exactly with their C counterparts. These are described in
|
||||
@xref{Functions with idiosyncratic bindings}.
|
||||
@item A few functions have been included in sb-posix that do not
|
||||
correspond exactly with their C counterparts. These are described
|
||||
in @ref{sb posix idiosyncracies}.
|
||||
@end itemize
|
||||
|
||||
@end enumerate
|
||||
|
||||
@node Function Return Values
|
||||
@node sb posix function return values
|
||||
@subsection Function Return Values
|
||||
|
||||
The return value is usually the same as for the C binding, except in
|
||||
error cases: where the C function is defined as returning some sentinel
|
||||
value and setting @code{errno} on error, we instead signal an error of
|
||||
type @code{SYSCALL-ERROR}. The actual error value (@code{errno}) is
|
||||
stored in this condition and can be accessed with @code{SYSCALL-ERRNO}.
|
||||
error cases: where the C function is defined as returning some
|
||||
sentinel value and setting @code{errno} on error, we instead signal an
|
||||
error of type @code{sb-posix:syscall-error}. The actual error
|
||||
value (@code{errno}) is stored in this condition and can be accessed with
|
||||
@code{sb-posix:syscall-errno}.
|
||||
|
||||
We do not automatically translate the returned value into ``Lispy''
|
||||
objects -- for example, @code{SB-POSIX:OPEN} returns a small integer,
|
||||
not a stream. Exception: boolean-returning functions (or, more
|
||||
commonly, macros) do not return a C integer, but instead a Lisp
|
||||
boolean.
|
||||
We do not automatically translate the returned value into lispy
|
||||
objects -- for example, @code{sb-posix:open} returns a small integer, not a
|
||||
stream. Exception: boolean-returning functions (or, more commonly,
|
||||
macros) do not return a C integer but instead a Lisp boolean.
|
||||
|
||||
@node Lisp objects and C structures
|
||||
@subsection Lisp objects and C structures
|
||||
@node sb posix lisp objects and c structures
|
||||
@subsection Lisp Objects and C structures
|
||||
|
||||
Sb-posix provides various Lisp object types to stand in for C
|
||||
structures in the POSIX library. Lisp bindings to C functions that
|
||||
|
|
@ -153,68 +208,110 @@ accept, manipulate, or return C structures accept, manipulate, or
|
|||
return instances of these Lisp types instead of instances of alien
|
||||
types.
|
||||
|
||||
The names of the Lisp types are chosen according to the general rules
|
||||
described above. For example Lisp objects of type @code{STAT} stand
|
||||
in for C structures of type @code{struct stat}.
|
||||
|
||||
Accessors are provided for each standard field in the structure. These
|
||||
are named @code{@var{structure-name}-@var{field-name}} where the two
|
||||
components are chosen according to the general name conversion rules,
|
||||
with the exception that in cases where all fields in a given structure
|
||||
have a common prefix, that prefix is omitted. For example,
|
||||
@code{stat.st_dev} in C becomes @code{STAT-DEV} in Lisp.
|
||||
|
||||
@c This was in the README, but it proves to be false about sb-posix.
|
||||
@ignore
|
||||
For each Lisp object type corresponding to a C structure type, there
|
||||
is a @code{make-@var{structure-name}} function that takes keyword
|
||||
arguments with names deriving from each documented field name
|
||||
according to the name conversion rules for accessors.
|
||||
@end ignore
|
||||
The names of the Lisp types are chosen according to the general
|
||||
rules described above. For example Lisp objects of type
|
||||
@code{sb-posix:stat} stand in for C structures of type @code{struct stat}.
|
||||
|
||||
Accessors are provided for each standard field in the structure.
|
||||
These are named @code{<structure-name>-<field-name>} where the two
|
||||
components are chosen according to the general name conversion
|
||||
rules, with the exception that in cases where all fields in a given
|
||||
structure have a common prefix, that prefix is omitted. For example,
|
||||
@code{stat.st_dev} in C becomes @code{stat-dev} in Lisp.
|
||||
|
||||
Because sb-posix might not support all semi-standard or
|
||||
implementation-dependent members of all structure types on your system
|
||||
(patches welcome), here is an enumeration of all supported Lisp
|
||||
objects corresponding to supported POSIX structures, and the supported
|
||||
slots for those structures.
|
||||
implementation-dependent members of all structure types on your
|
||||
system (patches welcome), here is an enumeration of all supported
|
||||
Lisp objects corresponding to supported POSIX structures, and the
|
||||
supported slots for those structures.
|
||||
|
||||
@include class-sb-posix-flock.texinfo
|
||||
@include class-sb-posix-passwd.texinfo
|
||||
@include class-sb-posix-group.texinfo
|
||||
@include class-sb-posix-stat.texinfo
|
||||
@include class-sb-posix-termios.texinfo
|
||||
@include class-sb-posix-timeval.texinfo
|
||||
|
||||
@node Functions with idiosyncratic bindings
|
||||
@subsection Functions with idiosyncratic bindings
|
||||
@anchor{Class sb-posix flock}
|
||||
@ttindex @sortas{flock sb-posix} flock [sb-posix]
|
||||
@deffn{Class} sb-posix:flock
|
||||
Class representing locks used in @code{fcntl(2)}.
|
||||
@end deffn
|
||||
@anchor{Class sb-posix passwd}
|
||||
@ttindex @sortas{passwd sb-posix} passwd [sb-posix]
|
||||
@deffn{Class} sb-posix:passwd
|
||||
Instances of this class represent entries in the system's user database.
|
||||
@end deffn
|
||||
@anchor{Class sb-posix group}
|
||||
@ttindex @sortas{group sb-posix} group [sb-posix]
|
||||
@deffn{Class} sb-posix:group
|
||||
Instances of this class represent entries in the system's group database.
|
||||
@end deffn
|
||||
@anchor{Class sb-posix stat}
|
||||
@ttindex @sortas{stat sb-posix} stat [sb-posix]
|
||||
@deffn{Class} sb-posix:stat
|
||||
Instances of this class represent POSIX file metadata.
|
||||
@end deffn
|
||||
@anchor{Class sb-posix termios}
|
||||
@ttindex @sortas{termios sb-posix} termios [sb-posix]
|
||||
@deffn{Class} sb-posix:termios
|
||||
Instances of this class represent I/O characteristics of the terminal.
|
||||
@end deffn
|
||||
@anchor{Class sb-posix timeval}
|
||||
@ttindex @sortas{timeval sb-posix} timeval [sb-posix]
|
||||
@deffn{Class} sb-posix:timeval
|
||||
Instances of this class represent time values.
|
||||
@end deffn
|
||||
@node sb posix idiosyncracies
|
||||
@subsection Functions with Idiosyncratic Bindings
|
||||
|
||||
A few functions in sb-posix don't correspond directly to their C
|
||||
counterparts.
|
||||
|
||||
@include fun-sb-posix-getcwd.texinfo
|
||||
@include fun-sb-posix-readlink.texinfo
|
||||
@include fun-sb-posix-syslog.texinfo
|
||||
|
||||
|
||||
@node Extensions to POSIX
|
||||
@anchor{Function sb-posix getcwd}
|
||||
@ffindex @sortas{getcwd sb-posix} getcwd [sb-posix]
|
||||
@deffn{Function} sb-posix:getcwd
|
||||
Returns the process's current working directory as a string.
|
||||
@end deffn
|
||||
@anchor{Function sb-posix readlink}
|
||||
@ffindex @sortas{readlink sb-posix} readlink [sb-posix]
|
||||
@deffn{Function} sb-posix:readlink pathspec
|
||||
Returns the resolved target of a symbolic link as a string.
|
||||
@end deffn
|
||||
@anchor{Function sb-posix syslog}
|
||||
@ffindex @sortas{syslog sb-posix} syslog [sb-posix]
|
||||
@deffn{Function} sb-posix:syslog priority format &rest args
|
||||
Send a message to the syslog facility, with severity level
|
||||
@code{priority}. The message will be formatted as by @code{cl:format} (rather
|
||||
than C's @code{printf}) with format string @code{format} and arguments @code{args}.
|
||||
@end deffn
|
||||
@node sb posix extensions to posix
|
||||
@subsection Extensions to POSIX
|
||||
|
||||
Some of POSIX's standardized operators are not safe to use on their
|
||||
own, so @code{SB-POSIX} exports a few ``helpers'' that do not
|
||||
correspond exactly to functionality present in the POSIX standard.
|
||||
own, so @code{sb-posix} exports a few helpers that do not correspond
|
||||
exactly to functionality present in the POSIX standard.
|
||||
|
||||
The user and group database accessing routines are not required to be
|
||||
thread-safe or reentrant, and so can only be used safely if all
|
||||
The user and group database accessing routines are not required to
|
||||
be thread-safe or reentrant and so can only be used safely if all
|
||||
clients coordinate around their use. Since it would be logically
|
||||
impossible for independently developed programs to coordinate,
|
||||
@code{SB-POSIX} exports two iteration macros,
|
||||
@code{SB-POSIX:DO-PASSWDS} and
|
||||
@code{SB-POSIX:DO-GROUPS}, each of which iterates over the respective
|
||||
database while preventing the keyed accesses (@code{SB-POSIX:GETPWNAM},
|
||||
@code{SB-POSIX:GETPWUID}, @code{SB-POSIX:GETGRNAM},
|
||||
@code{SB-POSIX:GETGRGID})
|
||||
from running until iteration completes.
|
||||
@code{sb-posix} exports two iteration macros, @code{sb-posix:do-passwds} and
|
||||
@code{sb-posix:do-groups}, each of which iterates over the respective
|
||||
database while preventing the keyed accesses (@code{sb-posix:getpwnam},
|
||||
@code{sb-posix:getpwuid}, @code{sb-posix:getgrnam}, @code{sb-posix:getgrgid}) from
|
||||
running until iteration completes.
|
||||
|
||||
@include macro-sb-posix-do-passwds.texinfo
|
||||
@include macro-sb-posix-do-groups.texinfo
|
||||
@anchor{Macro sb-posix do-passwds}
|
||||
@ffindex @sortas{do-passwds sb-posix} do-passwds [sb-posix]
|
||||
@deffn{Macro} sb-posix:do-passwds (passwd &optional result) &body body
|
||||
Evaluate @code{body} with @code{passwd} bound to successive entries from the passwd
|
||||
database, and return @code{result}. An implicit block named @code{nil} surrounds
|
||||
the form; an implicit @code{tagbody} surrounds @code{body}. It is unspecified
|
||||
whether @code{passwd} is assigned, rebound, or destructively modified upon
|
||||
each iteration. It is an error to use any operator that accesses the
|
||||
@code{passwd} database during the dynamic extent of @code{do-passwds}.
|
||||
@end deffn
|
||||
@anchor{Macro sb-posix do-groups}
|
||||
@ffindex @sortas{do-groups sb-posix} do-groups [sb-posix]
|
||||
@deffn{Macro} sb-posix:do-groups (group &optional result) &body body
|
||||
Evaluate @code{body} with @code{group} bound to successive entries from the group
|
||||
database, and return @code{result}. An implicit block named @code{nil} surrounds
|
||||
the form; an implicit @code{tagbody} surrounds @code{body}. It is unspecified
|
||||
whether @code{group} is assigned, rebound, or destructively modified upon
|
||||
each iteration. It is an error to use any operator that accesses the
|
||||
@code{group} database during the dynamic extent of @code{do-groups}.
|
||||
@end deffn
|
||||
|
|
|
|||
|
|
@ -1,6 +1,8 @@
|
|||
@node sb-queue
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node sb queue
|
||||
@section sb-queue
|
||||
@cindex Queue, FIFO
|
||||
|
||||
Since SBCL 1.0.38, the @code{sb-queue} module has been merged into the
|
||||
@code{sb-concurrency} module (@pxref{sb-concurrency}.)
|
||||
@code{sb-concurrency} module. See @ref{sb concurrency}.
|
||||
|
||||
|
|
|
|||
|
|
@ -1,18 +1,22 @@
|
|||
@node sb-rotate-byte
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node sb rotate byte
|
||||
@section sb-rotate-byte
|
||||
@cindex Modular arithmetic
|
||||
@cindex Arithmetic, modular
|
||||
@cindex Arithmetic, hardware
|
||||
|
||||
The @code{sb-rotate-byte} module offers an interface to bitwise
|
||||
rotation, with an efficient implementation for operations which can be
|
||||
performed directly using the platform's arithmetic routines. It
|
||||
implements the specification at
|
||||
@uref{http://www.cliki.net/ROTATE-BYTE}.
|
||||
@comment FIXME: except when someone scribbles all over it. Hmm.
|
||||
rotation, with an efficient implementation for operations which can
|
||||
be performed directly using the platform's arithmetic routines. It
|
||||
implements the specification at @url{http://www.cliki.net/ROTATE-BYTE}.
|
||||
|
||||
Bitwise rotation is a component of various cryptographic or hashing
|
||||
algorithms: MD5, SHA-1, etc.; often these algorithms are specified on
|
||||
32-bit rings. [FIXME cite cite cite].
|
||||
algorithms: MD5, SHA-1, etc.; often these algorithms are specified
|
||||
on 32-bit rings.
|
||||
|
||||
@include fun-sb-rotate-byte-rotate-byte.texinfo
|
||||
@anchor{Function sb-rotate-byte rotate-byte}
|
||||
@ffindex @sortas{rotate-byte sb-rotate-byte} rotate-byte [sb-rotate-byte]
|
||||
@deffn{Function} sb-rotate-byte:rotate-byte count bytespec integer
|
||||
Rotates a field of bits within @code{integer}; specifically, returns an
|
||||
integer that contains the bits of @code{integer} rotated @code{count} times
|
||||
leftwards within the byte specified by @code{bytespec}, and elsewhere
|
||||
contains the bits of @code{integer}.
|
||||
@end deffn
|
||||
|
|
|
|||
|
|
@ -1,25 +1,27 @@
|
|||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node sb simple streams
|
||||
@section Simple Streams
|
||||
|
||||
Simple streams are an extensible streams protocol that avoids some
|
||||
problems with Gray streams.
|
||||
problems with @ref{gray streams}.
|
||||
|
||||
Documentation about simple streams is available at:
|
||||
|
||||
@uref{http://www.franz.com/support/documentation/6.2/doc/streams.htm}
|
||||
@url{http://www.franz.com/support/documentation/6.2/doc/streams.htm}
|
||||
|
||||
The implementation should be considered Alpha-quality; the basic
|
||||
framework is there, but many classes are just stubs at the moment.
|
||||
|
||||
See @file{SYS:CONTRIB;SB-SIMPLE-STREAMS;SIMPLE-STREAM-TEST.LISP} for
|
||||
See @code{SYS:CONTRIB;SB-SIMPLE-STREAMS;SIMPLE-STREAM-TEST.LISP} for
|
||||
things that should work.
|
||||
|
||||
Known differences to the ACL behaviour:
|
||||
|
||||
@itemize
|
||||
@item @code{sb-simple-streams:open} does not return a @code{simple-stream} by
|
||||
default. See its @code{:class} argument.
|
||||
|
||||
@item
|
||||
@code{open} not return a simple-stream by default. This can be
|
||||
adjusted; see default-open-class in the file cl.lisp
|
||||
|
||||
@item
|
||||
@code{write-vector} is unimplemented.
|
||||
|
||||
@item @code{write-vector} is unimplemented.
|
||||
@end itemize
|
||||
|
||||
|
|
|
|||
|
|
@ -1,23 +1,28 @@
|
|||
@cindex Profiling, statistical
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node statistical profiler
|
||||
@section Statistical Profiler
|
||||
|
||||
The @code{sb-sprof} module, loadable by
|
||||
@lisp
|
||||
|
||||
@example
|
||||
(require :sb-sprof)
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
provides an alternate profiler which works by taking samples of the
|
||||
program execution at regular intervals, instead of instrumenting
|
||||
functions like @code{sb-profile:profile} does. You might find
|
||||
@code{sb-sprof} more useful than the deterministic profiler when profiling
|
||||
functions in the @code{common-lisp}-package, SBCL internals, or code
|
||||
where the instrumenting overhead is excessive.
|
||||
functions as @code{sb-profile:profile} does. You might find @code{sb-sprof} more
|
||||
useful than the deterministic profiler when profiling functions in the
|
||||
@code{common-lisp} package, SBCL internals, or code where the instrumenting
|
||||
overhead is excessive.
|
||||
|
||||
Additionally @code{sb-sprof} includes a limited deterministic profiler
|
||||
which can be used for reporting the amounts of calls to some functions
|
||||
during
|
||||
|
||||
@subsection Example Usage
|
||||
@strong{Example usage:}
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(in-package :cl-user)
|
||||
|
||||
(require :sb-sprof)
|
||||
|
|
@ -71,15 +76,15 @@ during
|
|||
:mode :alloc
|
||||
:report :flat)
|
||||
(bar 1000))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
@subsection Output
|
||||
@strong{Output:}
|
||||
|
||||
The flat report format will show a table of all functions that the
|
||||
profiler encountered on the call stack during sampling, ordered by the
|
||||
number of samples taken while executing that function.
|
||||
profiler encountered on the call stack during sampling, ordered by
|
||||
the number of samples taken while executing that function.
|
||||
|
||||
@lisp
|
||||
@example
|
||||
Self Total Cumul
|
||||
Nr Count % Count % Count % Calls Function
|
||||
------------------------------------------------------------------------
|
||||
|
|
@ -87,26 +92,26 @@ number of samples taken while executing that function.
|
|||
2 64 22.6 64 22.6 133 47.0 - SB-VM::GENERIC-+
|
||||
3 39 13.8 256 90.5 172 60.8 1 CPU-TEST
|
||||
4 31 11.0 31 11.0 203 71.7 - SB-KERNEL:TWO-ARG-XOR
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
For each function, the table will show three absolute and relative
|
||||
sample counts. The Self column shows samples taken while directly
|
||||
executing that function. The Total column shows samples taken while
|
||||
executing that function or functions called from it (sampled to a
|
||||
platform-specific depth). The Cumul column shows the sum of all
|
||||
Self columns up to and including that line in the table.
|
||||
sample counts. The @code{Self} column shows samples taken while directly
|
||||
executing that function. The @code{Total} column shows samples taken
|
||||
while executing that function or functions called from it (sampled
|
||||
to a platform-specific depth). The @code{Cumul} column shows the sum of
|
||||
all @code{Self} columns up to and including that line in the table.
|
||||
|
||||
Additionally the Calls column will record the amount of calls that were
|
||||
made to the function during the profiling run. This value will only
|
||||
be reported for functions that have been explicitly marked for call counting
|
||||
with @code{profile-call-counts}.
|
||||
Additionally the @code{Calls} column will record the amount of calls that
|
||||
were made to the function during the profiling run. This value will
|
||||
only be reported for functions that have been explicitly marked for
|
||||
call counting with @code{sb-sprof:profile-call-counts}.
|
||||
|
||||
The profiler also hooks into the disassembler such that instructions which
|
||||
have been sampled are annotated with their relative frequency of
|
||||
sampling. This information is not stored across different sampling
|
||||
runs.
|
||||
The profiler also hooks into the disassembler such that instructions
|
||||
which have been sampled are annotated with their relative frequency
|
||||
of sampling. This information is not stored across different
|
||||
sampling runs.
|
||||
|
||||
@lisp
|
||||
@example
|
||||
; 6CF: 702E JO L4 ; 6/242 samples
|
||||
; 6D1: D1E3 SHL EBX, 1
|
||||
; 6D3: 702A JO L4
|
||||
|
|
@ -114,44 +119,231 @@ runs.
|
|||
; 6D8: 756D JNE L8
|
||||
; 6DA: 8BC3 MOV EAX, EBX ; 5/242 samples
|
||||
; 6DC: L3: 83F900 CMP ECX, 0 ; 4/242 samples
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
@subsection Platform support
|
||||
@strong{Platform support}
|
||||
|
||||
Allocation profiling is only supported on SBCL builds that use
|
||||
the generational garbage collector. Tracking of call stacks at a
|
||||
depth of more than two levels is only supported on x86 and x86-64.
|
||||
Allocation profiling is only supported on SBCL builds that use the
|
||||
generational garbage collector. Tracking of call stacks at a depth
|
||||
of more than two levels is only supported on x86 and x86-64.
|
||||
|
||||
@subsection Macros
|
||||
@strong{Macros}
|
||||
|
||||
@include macro-sb-sprof-with-profiling.texinfo
|
||||
@include macro-sb-sprof-with-sampling.texinfo
|
||||
@anchor{Macro sb-sprof with-profiling}
|
||||
@ffindex @sortas{with-profiling sb-sprof} with-profiling [sb-sprof]
|
||||
@deffn{Macro} sb-sprof:with-profiling (&key sample-interval alloc-interval max-samples reset mode loop max-depth show-progress threads report) &body body
|
||||
Evaluate @code{body} with statistical profiling turned on. If @code{loop} is true,
|
||||
loop around the @code{body} until a sufficient number of samples has been collected.
|
||||
Returns the values from the last evaluation of @code{body}.
|
||||
|
||||
@subsection Functions
|
||||
The following keyword args are recognized:
|
||||
|
||||
@include fun-sb-sprof-map-traces.texinfo
|
||||
@itemize
|
||||
@item @code{:sample-interval} @code{<n>}
|
||||
|
||||
@include fun-sb-sprof-sample-pc.texinfo
|
||||
Take a sample every <n> seconds. Default is @code{*sample-interval*}.
|
||||
|
||||
@include fun-sb-sprof-report.texinfo
|
||||
@item @code{:mode} @code{<mode>}
|
||||
|
||||
@include fun-sb-sprof-reset.texinfo
|
||||
If @code{:cpu}, run the profiler in CPU profiling mode. If @code{:alloc}, run
|
||||
the profiler in allocation profiling mode. If @code{:time}, run the
|
||||
profiler in wallclock profiling mode.
|
||||
|
||||
@include fun-sb-sprof-start-profiling.texinfo
|
||||
@item @code{:max-samples} @code{<max>}
|
||||
|
||||
@include fun-sb-sprof-stop-profiling.texinfo
|
||||
If @code{:loop} is @code{nil} (the default), collect no more than @code{<max>}
|
||||
samples. If @code{:loop} is @code{t}, repeat evaluating body until @code{<max>}
|
||||
samples are taken. Default is @code{*max-samples*}.
|
||||
|
||||
@include fun-sb-sprof-profile-call-counts.texinfo
|
||||
@item @code{:report} @code{<type>}
|
||||
|
||||
@include fun-sb-sprof-unprofile-call-counts.texinfo
|
||||
If specified, call @code{report} with @code{:type} @code{<type>} at the end.
|
||||
|
||||
@subsection Variables
|
||||
@item @code{:reset} @code{<bool>}
|
||||
|
||||
@include var-sb-sprof-star-max-samples-star.texinfo
|
||||
If true, call @code{reset} at the beginning.
|
||||
|
||||
@include var-sb-sprof-star-sample-interval-star.texinfo
|
||||
@item @code{:threads} @code{<list-form>}
|
||||
|
||||
@subsection Credits
|
||||
Form that evaluates to the list threads to profile, or @code{:all} to
|
||||
indicate that all threads should be profiled. Defaults to all
|
||||
threads.
|
||||
|
||||
@code{:threads} has no effect on call-counting at the moment.
|
||||
|
||||
On some platforms (e.g. Darwin) the signals used by the profiler
|
||||
are not properly delivered to threads in proportion to their CPU
|
||||
usage when doing @code{:cpu} profiling. If you see empty call graphs, or
|
||||
are obviously missing several samples from certain threads, you
|
||||
may be falling afoul of this. In this case using @code{:mode} @code{:time} is
|
||||
likely to work better.
|
||||
|
||||
@item @code{:loop} @code{<bool>}
|
||||
|
||||
If false (the default), evaluate @code{body} only once. If true
|
||||
repeatedly evaluate @code{body}.
|
||||
@end itemize
|
||||
@end deffn
|
||||
@anchor{Macro sb-sprof with-sampling}
|
||||
@ffindex @sortas{with-sampling sb-sprof} with-sampling [sb-sprof]
|
||||
@deffn{Macro} sb-sprof:with-sampling (&optional on) &body body
|
||||
Evaluate body with statistical sampling turned on or off in the current thread.
|
||||
@end deffn
|
||||
@strong{Functions}
|
||||
|
||||
@anchor{Function sb-sprof map-traces}
|
||||
@ffindex @sortas{map-traces sb-sprof} map-traces [sb-sprof]
|
||||
@deffn{Function} sb-sprof:map-traces function samples
|
||||
Call @code{function} on each trace in @code{samples}
|
||||
|
||||
The signature of @code{function} must be compatible with (thread trace).
|
||||
|
||||
@code{function} is called once for each trace where @code{thread} is the
|
||||
@code{sb-thread:thread} instance that was sampled to produce @code{trace}, and @code{trace}
|
||||
is an opaque object to be passed to @code{map-trace-pc-locs}.
|
||||
|
||||
EXPERIMENTAL: Interface subject to change.
|
||||
@end deffn
|
||||
@anchor{Function sb-sprof sample-pc}
|
||||
@ffindex @sortas{sample-pc sb-sprof} sample-pc [sb-sprof]
|
||||
@deffn{Function} sb-sprof:sample-pc info pc-or-offset
|
||||
Extract and return program counter from @code{info} and @code{pc-or-offset}.
|
||||
|
||||
Can be applied to the arguments passed by @code{map-trace-pc-locs} and
|
||||
@code{map-all-pc-locs}.
|
||||
|
||||
EXPERIMENTAL: Interface subject to change.
|
||||
@end deffn
|
||||
@anchor{Function sb-sprof report}
|
||||
@ffindex @sortas{report sb-sprof} report [sb-sprof]
|
||||
@deffn{Function} sb-sprof:report &key type max min-percent call-graph sort-by sort-order stream show-progress
|
||||
Report statistical profiling results. The following keyword
|
||||
args are recognized:
|
||||
|
||||
@itemize
|
||||
@item @code{:type} @code{<type>}
|
||||
|
||||
Specifies the type of report to generate. If @code{:flat}, show flat
|
||||
report, if @code{:graph} show a call graph and a flat report. If nil,
|
||||
don't print out a report.
|
||||
|
||||
@item @code{:stream} @code{<stream>}
|
||||
|
||||
Specify a stream to print the report on. Default is
|
||||
@code{*standard-output*}.
|
||||
|
||||
@item @code{:max} @code{<max>}
|
||||
|
||||
Don't show more than @code{<max>} entries in the flat report.
|
||||
|
||||
@item @code{:min-percent} @code{<min-percent>}
|
||||
|
||||
Don't show functions taking less than @code{<min-percent>} of the
|
||||
total time in the flat report.
|
||||
|
||||
@item @code{:sort-by} @code{<column>}
|
||||
|
||||
If @code{:samples}, sort flat report by number of samples taken.
|
||||
If @code{:cumulative-samples}, sort flat report by cumulative number of samples
|
||||
taken (shows how much time each function spent on stack.) Default
|
||||
is @code{*report-sort-by*}.
|
||||
|
||||
@item @code{:sort-order} @code{<order>}
|
||||
|
||||
If @code{:descending}, sort flat report in descending order. If @code{:ascending},
|
||||
sort flat report in ascending order. Default is @code{*report-sort-order*}.
|
||||
|
||||
@item @code{:show-progress} @code{<bool>}
|
||||
|
||||
If true, print progress messages while generating the call graph.
|
||||
|
||||
@item @code{:call-graph} @code{<graph>}
|
||||
|
||||
Print a report from @code{<graph>} instead of the latest profiling
|
||||
results.
|
||||
@end itemize
|
||||
|
||||
Value of this function is a @code{call-graph} object representing the
|
||||
resulting call-graph, or @code{nil} if there are no samples (e.g. right after
|
||||
calling @code{reset}.)
|
||||
|
||||
Profiling is stopped before the call graph is generated.
|
||||
@end deffn
|
||||
@anchor{Function sb-sprof reset}
|
||||
@ffindex @sortas{reset sb-sprof} reset [sb-sprof]
|
||||
@deffn{Function} sb-sprof:reset
|
||||
Reset the profiler.
|
||||
@end deffn
|
||||
@anchor{Function sb-sprof start-profiling}
|
||||
@ffindex @sortas{start-profiling sb-sprof} start-profiling [sb-sprof]
|
||||
@deffn{Function} sb-sprof:start-profiling &key max-samples mode sample-interval alloc-interval max-depth threads
|
||||
Start profiling statistically in the current thread if not already profiling.
|
||||
The following keyword args are recognized:
|
||||
|
||||
@itemize
|
||||
@item @code{:sample-interval} @code{<n>}
|
||||
|
||||
Take a sample every @code{<n>} seconds. Default is @code{*sample-interval*}.
|
||||
|
||||
@item @code{:mode} @code{<mode>}
|
||||
|
||||
If @code{:cpu}, run the profiler in CPU profiling mode. If @code{:alloc}, run
|
||||
the profiler in allocation profiling mode. If @code{:time}, run the
|
||||
profiler in wallclock profiling mode.
|
||||
|
||||
@item @code{:max-samples} @code{<max>}
|
||||
|
||||
Maximum number of stack traces to collect. Default is
|
||||
@code{*max-samples*}.
|
||||
|
||||
@item @code{:threads} @code{<list>}
|
||||
|
||||
List threads to profile, or @code{:all} to indicate that all threads
|
||||
should be profiled. Defaults to @code{:all}.
|
||||
|
||||
@code{:threads} has no effect on call-counting at the moment.
|
||||
|
||||
On some platforms (e.g. Darwin) the signals used by the profiler
|
||||
are not properly delivered to threads in proportion to their CPU
|
||||
usage when doing @code{:cpu} profiling. If you see empty call graphs, or
|
||||
are obviously missing several samples from certain threads, you
|
||||
may be falling afoul of this.
|
||||
@end itemize
|
||||
@end deffn
|
||||
@anchor{Function sb-sprof stop-profiling}
|
||||
@ffindex @sortas{stop-profiling sb-sprof} stop-profiling [sb-sprof]
|
||||
@deffn{Function} sb-sprof:stop-profiling
|
||||
Stop profiling if profiling.
|
||||
@end deffn
|
||||
@anchor{Function sb-sprof profile-call-counts}
|
||||
@ffindex @sortas{profile-call-counts sb-sprof} profile-call-counts [sb-sprof]
|
||||
@deffn{Function} sb-sprof:profile-call-counts &rest names
|
||||
Mark the functions named by @code{names} as being subject to call counting
|
||||
during statistical profiling. If a string is used as a name, it will
|
||||
be interpreted as a package name. In this case call counting will be
|
||||
done for all functions with names like @code{x} or @code{(setf x)}, where @code{x} is
|
||||
a symbol with the package as its home package.
|
||||
@end deffn
|
||||
@anchor{Function sb-sprof unprofile-call-counts}
|
||||
@ffindex @sortas{unprofile-call-counts sb-sprof} unprofile-call-counts [sb-sprof]
|
||||
@deffn{Function} sb-sprof:unprofile-call-counts
|
||||
Clear all call counting information. Call counting will be done for no
|
||||
functions during statistical profiling.
|
||||
@end deffn
|
||||
@strong{Variables}
|
||||
|
||||
@anchor{Variable sb-sprof *max-samples*}
|
||||
@vvindex @sortas{max-samples* sb-sprof} *max-samples* [sb-sprof]
|
||||
@deffn{Variable} sb-sprof:*max-samples*
|
||||
Default maximum number of stack traces collected.
|
||||
@end deffn
|
||||
@anchor{Variable sb-sprof *sample-interval*}
|
||||
@vvindex @sortas{sample-interval* sb-sprof} *sample-interval* [sb-sprof]
|
||||
@deffn{Variable} sb-sprof:*sample-interval*
|
||||
Default number of seconds between samples.
|
||||
@end deffn
|
||||
@strong{Credits}
|
||||
|
||||
@code{sb-sprof} is an SBCL port, with enhancements, of Gerd Moellmann's
|
||||
statistical profiler for CMUCL.
|
||||
|
||||
@code{sb-sprof} is an SBCL port, with enhancements, of Gerd
|
||||
Moellmann's statistical profiler for CMUCL.
|
||||
|
|
|
|||
1
doc/manual/.gitignore
vendored
1
doc/manual/.gitignore
vendored
|
|
@ -28,5 +28,6 @@ sbcl.info*
|
|||
sbcl.pdf
|
||||
sbcl.ps
|
||||
sbcl/
|
||||
sbcl-contento.texinfo
|
||||
variables.texinfo
|
||||
generated-texinfo-stamp
|
||||
|
|
|
|||
|
|
@ -1,6 +1,5 @@
|
|||
With the exception of sbcl.texinfo, backmatter.texinfo,
|
||||
sbcl-menu.texinf and sbcl-contents.texinfo all other Texinfo files are
|
||||
from SB-MANUAL::GENERATE-TEXINFO.
|
||||
With the exception of sbcl.texinfo, backmatter.texinfo, all other
|
||||
Texinfo files are from SB-MANUAL::GENERATE-TEXINFO.
|
||||
|
||||
With the exception of variables.texinfo, the generated files are under
|
||||
version control, to keep a closer eye on the Markdown-to-Texinfo
|
||||
|
|
|
|||
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
|
|
@ -1,52 +1,297 @@
|
|||
@node Contributed Modules
|
||||
@comment node-name, next, previous, up
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node contributed modules
|
||||
@chapter Contributed Modules
|
||||
|
||||
@menu
|
||||
* sb-aclrepl: sb aclrepl.
|
||||
* sb-concurrency: sb concurrency.
|
||||
* sb-cover: sb cover.
|
||||
* sb-grovel: sb grovel.
|
||||
* sb-introspect: sb introspect.
|
||||
* sb-manual: sb manual.
|
||||
* sb-md5: sb md5.
|
||||
* sb-posix: sb posix.
|
||||
* sb-queue: sb queue.
|
||||
* sb-rotate-byte: sb rotate byte.
|
||||
* sb-simd: sb simd.
|
||||
@end menu
|
||||
|
||||
SBCL comes with a number of modules that are not part of the core
|
||||
system. These are loaded via @code{(require :@var{modulename})}
|
||||
(@pxref{Customization Hooks for Users}). This section contains
|
||||
system. These are loaded via @code{(require :<modulename>)}
|
||||
(see @ref{customization hooks for users}). This section contains
|
||||
documentation (or pointers to documentation) for some of the
|
||||
contributed modules.
|
||||
|
||||
@include ../../contrib/sb-aclrepl/sb-aclrepl.texinfo
|
||||
@include ../../contrib/sb-concurrency/sb-concurrency.texinfo
|
||||
@include ../../contrib/sb-cover/sb-cover.texinfo
|
||||
@include ../../contrib/sb-grovel/sb-grovel.texinfo
|
||||
@include ../../contrib/sb-introspect/sb-introspect.texinfo
|
||||
@include ../../contrib/sb-manual/sb-manual.texinfo
|
||||
@include ../../contrib/sb-md5/sb-md5.texinfo
|
||||
@include ../../contrib/sb-posix/sb-posix.texinfo
|
||||
@include ../../contrib/sb-queue/sb-queue.texinfo
|
||||
@include ../../contrib/sb-rotate-byte/sb-rotate-byte.texinfo
|
||||
@node sb simd
|
||||
@section sb-simd
|
||||
|
||||
@menu
|
||||
* sb-aclrepl::
|
||||
* sb-concurrency::
|
||||
* sb-cover::
|
||||
* sb-grovel::
|
||||
* sb-introspect::
|
||||
* sb-md5::
|
||||
* sb-posix::
|
||||
* sb-queue::
|
||||
* sb-rotate-byte::
|
||||
* sb-simd::
|
||||
* Data Types: data types.
|
||||
* Casts: casts.
|
||||
* Constructors: constructors.
|
||||
* Unpackers: unpackers.
|
||||
* Reinterpret Casts: reinterpret casts.
|
||||
* Associatives: associatives.
|
||||
* Reducers: reducers.
|
||||
* Rounding: rounding.
|
||||
* Comparisons: comparisons.
|
||||
* Conditionals: conditionals.
|
||||
* Loads and Stores: loads and stores.
|
||||
* Specialized Scalar Operations: specialized scalar operations.
|
||||
* Instruction Set Dispatch: instruction set dispatch.
|
||||
@end menu
|
||||
|
||||
@page
|
||||
@include sb-aclrepl/sb-aclrepl.texinfo
|
||||
The @code{sb-simd} module provides a convenient interface for SIMD
|
||||
programming in SBCL. It provides one package per SIMD instruction
|
||||
set, plus functions and macros for querying whether an instruction
|
||||
set is available and what functions and data types it exports.
|
||||
|
||||
@page
|
||||
@include sb-concurrency/sb-concurrency.texinfo
|
||||
@node data types
|
||||
@subsection Data Types
|
||||
|
||||
@page
|
||||
@include sb-cover/sb-cover.texinfo
|
||||
The central data type in sb-simd is the SIMD pack. A SIMD pack
|
||||
is very similar to a specialized vector, except that its length must
|
||||
be a particular power of two that depends on its element type and
|
||||
the underlying hardware. The set of element types that are supported
|
||||
for SIMD packs is similar to that of SBCL's specialized array
|
||||
element types, except that there is currently no support for SIMD
|
||||
packs of complex numbers or characters.
|
||||
|
||||
@page
|
||||
@include sb-grovel/sb-grovel.texinfo
|
||||
The supported scalar types are @code{f32}, @code{f64}, @code{s<n>}, and @code{u<n>},
|
||||
where @code{<n>} is either 8, 16, 32, or 64. These scalar types are
|
||||
abbreviations for the Common Lisp types @code{single-float}, @code{double-float},
|
||||
@code{signed-byte}, and @code{unsigned-byte}, respectively. For each scalar data
|
||||
type @code{x}, there exists one or more SIMD data type @code{x.y} with @code{y}
|
||||
elements. For example, in AVX there are two supported SIMD data
|
||||
types with element type @code{f64}, namely @code{f64.2} (128 bit) and
|
||||
@code{f64.4} (256 bit).
|
||||
|
||||
@page
|
||||
@include sb-introspect/sb-introspect.texinfo
|
||||
SIMD packs are regular Common Lisp objects that have a type, a
|
||||
class, and can be passed as function arguments. The price for this
|
||||
is that SIMD packs have both a boxed and an unboxed representation.
|
||||
The unboxed representation of a SIMD pack has zero overhead and fits
|
||||
into a CPU register but can only be used within a function and when
|
||||
the compiler can statically determine the SIMD pack's type.
|
||||
Otherwise, the SIMD pack is boxed, i.e. spilled to the heap together
|
||||
with its type information. In practice, boxing of SIMD packs can
|
||||
usually be avoided via inlining, or by loading and storing them to
|
||||
specialized arrays instead of passing them around as function
|
||||
arguments.
|
||||
|
||||
@page
|
||||
@include sb-md5/sb-md5.texinfo
|
||||
@node casts
|
||||
@subsection Casts
|
||||
|
||||
@page
|
||||
@include sb-posix/sb-posix.texinfo
|
||||
For each scalar data type @code{x}, there is a function named @code{x}
|
||||
that is equivalent to @code{(lambda (v) (coerce v 'x))}. For each SIMD
|
||||
data type @code{x.y}, there is a function named @code{x.y} that ensures that
|
||||
its argument is of type @code{x.y}, or, if the argument is a number,
|
||||
calls the cast function of @code{x} and broadcasts the result.
|
||||
|
||||
@page
|
||||
@include sb-queue/sb-queue.texinfo
|
||||
All functions provided by sb-simd (apart from the casts themselves)
|
||||
implicitly cast each argument to its expected type. So, to add the
|
||||
number five to each single float in a SIMD pack @code{x} of type @code{f32.8},
|
||||
it is sufficient to write @code{(f32.8+ x 5)}. We don't mention this
|
||||
implicit conversion explicitly in the following sections, so if any
|
||||
function description states that an argument must be of type @code{x.y},
|
||||
the argument can actually be of any type that is a suitable argument
|
||||
of the cast function named @code{x.y}.
|
||||
|
||||
@page
|
||||
@include sb-rotate-byte/sb-rotate-byte.texinfo
|
||||
@node constructors
|
||||
@subsection Constructors
|
||||
|
||||
For each SIMD data type @code{x.y}, there is a constructor named
|
||||
@code{make-x.y} that takes @code{y} arguments of type @code{x} and returns a SIMD
|
||||
pack whose elements are the supplied values.
|
||||
|
||||
@node unpackers
|
||||
@subsection Unpackers
|
||||
|
||||
For each SIMD data type @code{x.y}, there is a function named
|
||||
@code{x.y-values} that returns, as @code{y} multiple values, the elements of
|
||||
the supplied SIMD pack of type @code{x.y}.
|
||||
|
||||
@node reinterpret casts
|
||||
@subsection Reinterpret Casts
|
||||
|
||||
For each SIMD data type @code{x.y}, there is a function named
|
||||
@code{x.y!} that takes any SIMD pack or scalar datum and interprets its
|
||||
bits as a SIMD pack of type @code{x.y}. If the supplied datum has more
|
||||
bits than the resulting value, the excess bits are discarded. If the
|
||||
supplied datum has less bits than the resulting value, the missing
|
||||
bits are assumed to be zero.
|
||||
|
||||
@node associatives
|
||||
@subsection Associatives
|
||||
|
||||
For each associative binary function, e.g. @code{two-arg-x.y-op}, there
|
||||
is a function @code{x.y-op} that takes any number of arguments and
|
||||
combines them with this binary function in a tree-like fashion. If
|
||||
the binary function has an identity element, it is possible to call
|
||||
the function with zero arguments, in which case the identity element
|
||||
is returned. If there is no identity element, the function must
|
||||
receive at least one argument.
|
||||
|
||||
Examples of associative functions are @code{sb-simd-avx:f32.8+}, for
|
||||
summing any number of 256 bit packs of single floats, and
|
||||
@code{sb-simd-fma:u8.32-max}, for computing the element-wise maximum of
|
||||
one or more 256 bit packs of 8 bit integers.
|
||||
|
||||
@node reducers
|
||||
@subsection Reducers
|
||||
|
||||
For binary functions @code{two-arg-x.y-op} that are not associative but
|
||||
have a neutral element, there are functions @code{x.y-op} that take any
|
||||
positive number of arguments and return the reduction of all
|
||||
arguments with the binary function. In the special case of a single
|
||||
supplied argument, the binary function is invoked on the neutral
|
||||
element and that argument. Reducers have been introduced to generate
|
||||
Lisp-style subtraction and division functions.
|
||||
|
||||
Examples of reducers are @code{sb-simd-avx:f32.8/}, for successively
|
||||
dividing a pack of 32 bit single floats by all further supplied
|
||||
packs of 32 bit single floats, or @code{sb-simd-fma:u32.8-} for
|
||||
subtracting any number of supplied packs of 32 bit unsigned integers
|
||||
from the first supplied one, except in the case of a single
|
||||
argument, where @code{sb-simd-fma:u32.8-} simply negates all values in
|
||||
the pack.
|
||||
|
||||
@node rounding
|
||||
@subsection Rounding
|
||||
|
||||
For each floating-point SIMD data type @code{x.y}, there are several
|
||||
functions that round the values of a supplied SIMD pack to nearby
|
||||
floating-point values whose fractional digits are all zero. Those
|
||||
functions are @code{x.y-round}, @code{x.y-floor}, @code{x.y-ceiling}, and
|
||||
@code{x.y-truncate}, and they have the same semantics as the one argument
|
||||
versions of @code{cl:round}, @code{cl:floor}, @code{cl:ceiling}, and @code{cl:truncate},
|
||||
respectively.
|
||||
|
||||
@node comparisons
|
||||
@subsection Comparisons
|
||||
|
||||
For each SIMD data type @code{x.y}, there exist conversion functions
|
||||
@code{x.y<}, @code{x.y<=}, @code{x.y>}, @code{x.y>=}, and @code{x.y=} that check whether the
|
||||
supplied arguments are strictly monotonically increasing,
|
||||
monotonically increasing, strictly monotonically decreasing,
|
||||
monotonically decreasing, equal, or nowhere equal, respectively. In
|
||||
contrast to the Common Lisp functions @code{<}, @code{<=}, @code{>}, @code{>=}, @code{=}, and
|
||||
@code{/=}, the SIMD comparison functions don't return a generalized
|
||||
boolean but a SIMD pack of unsigned integers with @code{y} elements.
|
||||
The bits of each unsigned integer are either all one, if the values
|
||||
of the arguments at that position satisfy the test, or all zero, if
|
||||
they don't. We call a SIMD packs of such unsigned integers a mask.
|
||||
|
||||
@node conditionals
|
||||
@subsection Conditionals
|
||||
|
||||
The SIMD paradigm is inherently incompatible with fine-grained control
|
||||
flow. A piece of code containing an @code{if} special form cannot be
|
||||
vectorized in a straightforward way, because doing so would require
|
||||
as many instruction pointers and processor states as there are
|
||||
values in the desired SIMD data type. Instead, most SIMD instruction
|
||||
sets provide an operator for selecting values from one of two
|
||||
supplied SIMD packs based on a mask. The mask is a SIMD pack with as
|
||||
many elements as the other two arguments, but whose elements are
|
||||
unsigned integers whose bits must be either all zeros or all ones.
|
||||
This selection mechanism can be used to emulate the effect of an @code{if}
|
||||
special form, at the price that both operands have to be computed
|
||||
each time.
|
||||
|
||||
In sb-simd, all conditional operations and comparisons emit suitable
|
||||
mask fields, and there is a @code{x.y-if} function for each SIMD data
|
||||
type with element type @code{x} and number of elements @code{y} whose first
|
||||
arguments must be a suitable mask, whose second and third argument
|
||||
must be objects that can be converted to the SIMD data type @code{x.y},
|
||||
and that returns a value of type @code{x.y} where each element is from
|
||||
the second operand if the corresponding mask bits are set, and from
|
||||
the third operand if the corresponding mask bits are not set.
|
||||
|
||||
@node loads and stores
|
||||
@subsection Loads and Stores
|
||||
|
||||
In practice, a SIMD pack @code{x.y} is usually not constructed by
|
||||
calling its constructor but by loading @code{y} consecutive elements from
|
||||
a specialized array with element type @code{x}. The functions for doing
|
||||
so are called @code{x.y-aref} and @code{x.y-row-major-aref}, and have similar
|
||||
semantics as Common Lisp's @code{aref} and @code{row-major-aref}. In addition to
|
||||
that, some instruction sets provide the functions
|
||||
@code{x.y-non-temporal-aref} and @code{x.y-non-temporal-row-major-aref}, for
|
||||
accessing a memory location without loading the referenced values
|
||||
into the CPU's cache.
|
||||
|
||||
For each function @code{x.y-foo} for loading SIMD packs from an array,
|
||||
there also exists a corresponding function @code{(setf x.y-foo)} for
|
||||
storing a SIMD pack in the specified memory location. An exception
|
||||
to this rule is that some instruction sets (e.g., SSE) only provide
|
||||
functions for non-temporal stores but not for the corresponding
|
||||
non-temporal loads.
|
||||
|
||||
One difficulty when treating the data of a Common Lisp array as a
|
||||
SIMD pack is that some hardware instructions require a particular
|
||||
alignment of the address being referenced. Luckily, most
|
||||
architectures provide instructions for unaligned loads and stores
|
||||
that are, at least on modern CPUs, not slower than their aligned
|
||||
equivalents. So by default we translate all array references as
|
||||
unaligned loads and stores. An exception are the instructions for
|
||||
non-temporal loads and stores, that always require a certain
|
||||
alignment. We do not handle this case specially, so without special
|
||||
handling by the user, non-temporal loads and stores will only work
|
||||
on certain array indices that depend on the actual placement of that
|
||||
array in memory.
|
||||
|
||||
@node specialized scalar operations
|
||||
@subsection Specialized Scalar Operations
|
||||
|
||||
Finally, for each SIMD function @code{x.y-op} that applies a certain
|
||||
operation @code{op} element-wise to the @code{y} elements of type @code{x}, there
|
||||
exists also a functions @code{x-op} for applying that operation only to a
|
||||
single element. For example, the SIMD function @code{f64.4+} has a
|
||||
corresponding function @code{f64+} that differs from @code{cl:+} in that it
|
||||
only accepts arguments of type double float, and that it adds its
|
||||
supplied arguments in a fixed order that is the same as the one used
|
||||
by @code{f64.4}.
|
||||
|
||||
There are good reasons for exporting scalar functions from a SIMD
|
||||
library, too. The most obvious one is that they obey the same naming
|
||||
convention and hence make it easier to locate the correct functions.
|
||||
Another benefit is that the semantics of each scalar operation is
|
||||
precisely the same as that of the corresponding SIMD function, so
|
||||
they can be used to write reference implementations for testing. A
|
||||
final reason is that these scalar functions can be used to simplify
|
||||
the life of tools for automatic vectorization.
|
||||
|
||||
@node instruction set dispatch
|
||||
@subsection Instruction Set Dispatch
|
||||
|
||||
One challenge that is unique to image-based programming systems such as
|
||||
Lisp is that a program can run on one machine, be dumped as an image,
|
||||
and then resumed on another machine. While nobody expects this feature
|
||||
to work across machines with different architectures, it is quite likely
|
||||
that the machine where the image is dumped and the one where execution
|
||||
is resumed provide different instruction set extensions.
|
||||
|
||||
As a practical example, consider a game developer that develops software
|
||||
on an x86-64 machine with all SIMD extensions up to AVX2, but then dumps
|
||||
it as an image and ships it to a customer whose machine only supports
|
||||
SIMD extensions up to SSE2. Ideally, the image should contain multiple
|
||||
optimized versions of all crucial functions, and dynamically select the
|
||||
most appropriate version based on the instruction set extensions that
|
||||
are actually available.
|
||||
|
||||
This kind of run time instruction set dispatch is explicitly
|
||||
supported by means of the SB-SIMD-INTERNALS:INSTRUCTION-SET-CASE
|
||||
macro. The code resulting from an invocation of this macro compiles
|
||||
to an efficient jump table whose index is recomputed on each startup
|
||||
of the Lisp image.
|
||||
|
||||
@page
|
||||
@include sb-simd/sb-simd.texinfo
|
||||
|
|
|
|||
File diff suppressed because it is too large
Load diff
|
|
@ -1,279 +1,272 @@
|
|||
@node Deprecation
|
||||
@comment node-name, next, previous, up
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node deprecation
|
||||
@chapter Deprecation
|
||||
|
||||
@menu
|
||||
* Why Deprecate?: why deprecate?.
|
||||
* The Deprecation Pipeline: the deprecation pipeline.
|
||||
* Deprecation Conditions: deprecation conditions.
|
||||
* Introspecting Deprecation Information: introspecting deprecation information.
|
||||
* Deprecation Declaration: deprecation declaration.
|
||||
* Deprecation Examples: deprecation examples.
|
||||
* Deprecated Interfaces in SBCL: deprecated interfaces in sbcl.
|
||||
@end menu
|
||||
|
||||
In order to support evolution of interfaces in SBCL as well as in user
|
||||
code, SBCL allows declaring functions, variables and types as
|
||||
deprecated. Users of deprecated things are notified by means of warnings
|
||||
while the deprecated thing in question is still available.
|
||||
deprecated. Users of deprecated things are notified by means of
|
||||
warnings while the deprecated thing in question is still available.
|
||||
|
||||
This chapter documents the interfaces for being notified when using
|
||||
deprecated thing and declaring things as deprecated, the deprecation
|
||||
process used for SBCL interfaces, and lists legacy interfaces in various
|
||||
stages of deprecation.
|
||||
process used for SBCL interfaces, and lists legacy interfaces in
|
||||
various stages of deprecation.
|
||||
|
||||
@dfn{Deprecation} in this context should not be confused with those
|
||||
things the ANSI Common Lisp standard calls @dfn{deprecated}: the
|
||||
entirety of ANSI CL is supported by SBCL, and none of those interfaces
|
||||
are subject to censure.
|
||||
@emph{Deprecation} in this context should not be confused with those
|
||||
things the ANSI Common Lisp standard calls @emph{deprecated}: the
|
||||
entirety of ANSI CL is supported by SBCL, and none of those
|
||||
interfaces are subject to censure.
|
||||
|
||||
@menu
|
||||
* Why Deprecate?::
|
||||
* The Deprecation Pipeline::
|
||||
* Deprecation Conditions::
|
||||
* Introspecting Deprecation Information::
|
||||
* Deprecation Declaration::
|
||||
* Deprecation Examples::
|
||||
* Deprecated Interfaces in SBCL::
|
||||
@end menu
|
||||
|
||||
@node Why Deprecate?
|
||||
@comment node-name, next, previous, up
|
||||
@node why deprecate?
|
||||
@section Why Deprecate?
|
||||
@cindex Why Deprecate?
|
||||
|
||||
While generally speaking we try to keep SBCL changes as backwards
|
||||
compatible as feasible, there are situations when existing interfaces
|
||||
are deprecated:
|
||||
|
||||
@itemize
|
||||
|
||||
@item @strong{Broken Interfaces}
|
||||
|
||||
Sometimes it turns out that an interface is sufficiently misdesigned
|
||||
that fixing it would be worse than deprecating it and replacing it
|
||||
with another.
|
||||
Sometimes it turns out that an interface is sufficiently
|
||||
misdesigned that fixing it would be worse than deprecating it
|
||||
and replacing it with another.
|
||||
|
||||
This is typically the case when fixing the interface would change its
|
||||
semantics in ways that could break user code subtly: in such cases we
|
||||
may end up considering the obvious breakage caused by deprecation to
|
||||
be preferable.
|
||||
This is typically the case when fixing the interface would
|
||||
change its semantics in ways that could break user code subtly:
|
||||
in such cases we may end up considering the obvious breakage
|
||||
caused by deprecation to be preferable.
|
||||
|
||||
Another example are functions or macros whose current signature makes
|
||||
them hard or impossible to extend in the future: backwards compatible
|
||||
extensions would either make the interface intolerably hairy, or are
|
||||
sometimes outright impossible.
|
||||
Another example are functions or macros whose current signature
|
||||
makes them hard or impossible to extend in the future: backwards
|
||||
compatible extensions would either make the interface
|
||||
intolerably hairy, or are sometimes outright impossible.
|
||||
|
||||
@item @strong{Internal Interfaces}
|
||||
|
||||
SBCL has several internal interfaces that were never meant to be used
|
||||
in user code -- or at least never meant to be used in user code
|
||||
unwilling to track changes to SBCL internals.
|
||||
SBCL has several internal interfaces that were never meant to be
|
||||
used in user code -- or at least never meant to be used in user
|
||||
code unwilling to track changes to SBCL internals.
|
||||
|
||||
Ideally we'd like to be free to refactor our own internals as we
|
||||
please, without even going through the hassle of deprecating things.
|
||||
Sometimes, however, it turns out that our internal interfaces have
|
||||
several external users who aren't using them advisedly, but due to
|
||||
misunderstandings regarding their status or stability.
|
||||
Ideally, we'd like to be free to refactor our own internals as
|
||||
we please, without even going through the hassle of deprecating
|
||||
things. Sometimes, however, it turns out that our internal
|
||||
interfaces have several external users who aren't using them
|
||||
advisedly, but due to misunderstandings regarding their status
|
||||
or stability.
|
||||
|
||||
Consider a deprecated internal interface a reminder for SBCL
|
||||
maintainers not to delete the thing just yet, even though it is seems
|
||||
unused -- because it has external users.
|
||||
maintainers not to delete the thing just yet, even though it is
|
||||
seems unused -- because it has external users.
|
||||
|
||||
When internal interfaces are deprecated we try our best to provide
|
||||
supported alternatives.
|
||||
When internal interfaces are deprecated we try our best to
|
||||
provide supported alternatives.
|
||||
|
||||
@item @strong{Aesthetics & Ease of Maintenance}
|
||||
|
||||
Sometimes an interface isn't broken or internal, but just inconsistent
|
||||
somehow.
|
||||
Sometimes an interface isn't broken or internal but just
|
||||
inconsistent somehow.
|
||||
|
||||
This mostly happens only with historical interfaces inherited from
|
||||
CMUCL which often haven't been officially supported in SBCL before, or
|
||||
with new extensions to SBCL that haven't been around for very long in
|
||||
the first place.
|
||||
This mostly happens only with historical interfaces inherited
|
||||
from CMUCL which often haven't been officially supported in SBCL
|
||||
before, or with new extensions to SBCL that haven't been around
|
||||
for very long in the first place.
|
||||
|
||||
The alternative would be to keep the suboptimal version around
|
||||
forever, possibly alongside an improved version. Sometimes we may do
|
||||
just that, but because every line of code comes with a maintenance
|
||||
cost, sometimes we opt to deprecate the suboptimal version instead:
|
||||
SBCL doesn't have infinite developer resources.
|
||||
|
||||
We also believe that sometimes cleaning out legacy interfaces helps
|
||||
keep the whole system more comprehensible to users, and makes
|
||||
introspective tools such as
|
||||
@findex @cl{apropos}
|
||||
@code{apropos} more useful.
|
||||
forever, possibly alongside an improved version. Sometimes we
|
||||
may do just that, but because every line of code comes with a
|
||||
maintenance cost, sometimes we opt to deprecate the suboptimal
|
||||
version instead: SBCL doesn't have infinite developer resources.
|
||||
|
||||
We also believe that sometimes cleaning out legacy interfaces
|
||||
helps keep the whole system more comprehensible to users, and
|
||||
makes introspective tools such as @code{apropos} more useful.
|
||||
@end itemize
|
||||
|
||||
@node The Deprecation Pipeline
|
||||
@comment node-name, next, previous, up
|
||||
@node the deprecation pipeline
|
||||
@section The Deprecation Pipeline
|
||||
@cindex The Deprecation Pipeline
|
||||
|
||||
SBCL uses a @dfn{deprecation pipeline} with multiple stages: as time
|
||||
goes by, deprecated things move from earlier stages of deprecation to
|
||||
later stages before finally being removed. The intention is making users
|
||||
aware of necessary changes early but allowing a migration to new
|
||||
interfaces at a reasonable pace.
|
||||
SBCL uses a @emph{deprecation pipeline} with multiplestages: as
|
||||
time time goes by, deprecated things move from earlier stages of
|
||||
deprecation to later stages before finally being removed. The
|
||||
intention is making users aware of necessary changes early but
|
||||
allowing a migration to new interfaces at a reasonable pace.
|
||||
|
||||
Deprecation proceeds in three stages, each lasting approximately a
|
||||
year. In some cases it might move slower or faster, but one year per
|
||||
stage is what we aim at in general. During each stage warnings (and
|
||||
errors) of increasing severity are signaled, which note that the
|
||||
interface is deprecated, and point users towards any replacements when
|
||||
applicable.
|
||||
|
||||
@enumerate
|
||||
interface is deprecated, and point users towards any replacements
|
||||
when applicable.
|
||||
|
||||
@itemize
|
||||
@item @strong{Early Deprecation}
|
||||
|
||||
During early deprecation the interface is kept in working
|
||||
condition. However, when a thing in this deprecation stage is used, an
|
||||
@tindex @sbext{early-deprecation-warning}
|
||||
@code{sb-ext:early-deprecation-warning}, which is a
|
||||
@tindex @cl{style-warning}
|
||||
@code{style-warning}, is signaled at
|
||||
compile-time.
|
||||
condition. However, when a thing in this deprecation stage is
|
||||
used, an @code{sb-ext:early-deprecation-warning}, which is a
|
||||
@code{style-warning}, is signaled at compile-time.
|
||||
|
||||
The internals may change at this stage: typically because the interface
|
||||
is re-implemented on top of its successor. While we try to keep things
|
||||
as backwards-compatible as feasible (taking maintenance costs into account),
|
||||
sometimes semantics change slightly.
|
||||
The internals may change at this stage: typically because the
|
||||
interface is re-implemented on top of its successor. While we
|
||||
try to keep things as backwards-compatible as feasible (taking
|
||||
maintenance costs into account), sometimes semantics change
|
||||
slightly.
|
||||
|
||||
For example, when the spinlock API was deprecated, spinlock objects ceased
|
||||
to exist, and the whole spinlock API became a synonym for the mutex
|
||||
API -- so code using the spinlock API continued working, but silently
|
||||
switched to mutexes instead. However, if someone relied on
|
||||
For example, when the spinlock API was deprecated, spinlock
|
||||
objects ceased to exist, and the whole spinlock API became a
|
||||
synonym for the mutex API -- so code using the spinlock API
|
||||
continued working but silently switched to mutexes instead.
|
||||
However, if someone relied on
|
||||
|
||||
@code{(typep lock 'spinlock)}
|
||||
@example
|
||||
(typep lock 'spinlock)
|
||||
@end example
|
||||
|
||||
returning @code{NIL} for a mutexes, trouble could ensue.
|
||||
returning @code{nil} for a mutexes, trouble could ensue.
|
||||
|
||||
@item @strong{Late Deprecation}
|
||||
|
||||
During late deprecation the interface remains as it was during early
|
||||
deprecation, but the compile-time warning is upgraded: when a thing in
|
||||
this deprecation stage is used, a
|
||||
@tindex @sbext{late-deprecation-warning}
|
||||
@code{sb-ext:late-deprecation-warning},
|
||||
which is a full
|
||||
@tindex @cl{warning}
|
||||
@code{warning}, is signaled at compile-time.
|
||||
During late deprecation the interface remains as it was during
|
||||
early deprecation, but the compile-time warning is upgraded:
|
||||
when a thing in this deprecation stage is used, a
|
||||
@code{sb-ext:late-deprecation-warning}, which is a full @code{warning}, is
|
||||
signaled at compile-time.
|
||||
|
||||
@item @strong{Final Deprecation}
|
||||
|
||||
During final deprecation the symbols still exist. However, when a thing
|
||||
in this deprecation stage is used, a
|
||||
@tindex @sbext{final-deprecation-warning}
|
||||
@code{sb-ext:final-deprecation-warning},
|
||||
which is a full
|
||||
@tindex @cl{warning}
|
||||
@code{warning}, is signaled at compile-time and an
|
||||
@tindex @cl{error}
|
||||
@code{error} is signaled at run-time.
|
||||
During final deprecation the symbols still exist. However, when
|
||||
a thing in this deprecation stage is used, a
|
||||
@code{sb-ext:final-deprecation-warning}, which is a full @code{warning}, is
|
||||
signaled at compile-time and an @code{error} is signaled at run-time.
|
||||
|
||||
@item @strong{After Final Deprecation}
|
||||
|
||||
The interface is deleted entirely.
|
||||
@end itemize
|
||||
|
||||
@end enumerate
|
||||
|
||||
@node Deprecation Conditions
|
||||
@comment node-name, next, previous, up
|
||||
@node deprecation conditions
|
||||
@section Deprecation Conditions
|
||||
@cindex Deprecation Conditions
|
||||
|
||||
@tindex @sbext{deprecation-condition}
|
||||
@code{sb-ext:deprecation-condition} is the superclass of all
|
||||
deprecation-related warning and error conditions. All common slots and
|
||||
readers are defined in this condition class.
|
||||
|
||||
@include condition-sb-ext-deprecation-condition.texinfo
|
||||
|
||||
@include condition-sb-ext-early-deprecation-warning.texinfo
|
||||
|
||||
@include condition-sb-ext-late-deprecation-warning.texinfo
|
||||
|
||||
@include condition-sb-ext-final-deprecation-warning.texinfo
|
||||
|
||||
@include condition-sb-ext-deprecation-error.texinfo
|
||||
|
||||
@node Introspecting Deprecation Information
|
||||
@comment node-name, next, previous, up
|
||||
@anchor{Condition sb-ext deprecation-condition}
|
||||
@ttindex @sortas{deprecation-condition sb-ext} deprecation-condition [sb-ext]
|
||||
@deffn{Condition} sb-ext:deprecation-condition
|
||||
Superclass for deprecation-related error and warning
|
||||
conditions.
|
||||
@end deffn
|
||||
@anchor{Condition sb-ext early-deprecation-warning}
|
||||
@ttindex @sortas{early-deprecation-warning sb-ext} early-deprecation-warning [sb-ext]
|
||||
@deffn{Condition} sb-ext:early-deprecation-warning
|
||||
This warning is signaled when the use of a variable,
|
||||
function, type, etc. in @code{:early} deprecation is detected at
|
||||
compile-time. The use will work at run-time with no warning or
|
||||
error.
|
||||
@end deffn
|
||||
@anchor{Condition sb-ext late-deprecation-warning}
|
||||
@ttindex @sortas{late-deprecation-warning sb-ext} late-deprecation-warning [sb-ext]
|
||||
@deffn{Condition} sb-ext:late-deprecation-warning
|
||||
This warning is signaled when the use of a variable,
|
||||
function, type, etc. in @code{:late} deprecation is detected at
|
||||
compile-time. The use will work at run-time with no warning or
|
||||
error.
|
||||
@end deffn
|
||||
@anchor{Condition sb-ext final-deprecation-warning}
|
||||
@ttindex @sortas{final-deprecation-warning sb-ext} final-deprecation-warning [sb-ext]
|
||||
@deffn{Condition} sb-ext:final-deprecation-warning
|
||||
This warning is signaled when the use of a variable,
|
||||
function, type, etc. in @code{:final} deprecation is detected at
|
||||
compile-time. An error will be signaled at run-time.
|
||||
@end deffn
|
||||
@anchor{Condition sb-ext deprecation-error}
|
||||
@ttindex @sortas{deprecation-error sb-ext} deprecation-error [sb-ext]
|
||||
@deffn{Condition} sb-ext:deprecation-error
|
||||
This error is signaled at run-time when an attempt is made to use
|
||||
a thing that is in @code{:final} deprecation, i.e. call a function or access
|
||||
a variable.
|
||||
@end deffn
|
||||
@node introspecting deprecation information
|
||||
@section Introspecting Deprecation Information
|
||||
@cindex Introspecting Deprecation Information
|
||||
@comment TODO @findex @sbcltl{function-information}
|
||||
@comment TODO @findex @sbcltl{variable-information}
|
||||
|
||||
The deprecation status of functions and variables can be inspected
|
||||
using the @code{sb-cltl2:function-information} and
|
||||
@code{sb-cltl2:variable-information} functions provided by the
|
||||
@code{sb-cltl2} contributed module.
|
||||
@code{sb-cltl2:variable-information} functions provided by the @code{sb-cltl2}
|
||||
contributed module.
|
||||
|
||||
@node Deprecation Declaration
|
||||
@comment node-name, next, previous, up
|
||||
@node deprecation declaration
|
||||
@section Deprecation Declaration
|
||||
@cindex Deprecation Declaration
|
||||
@findex @sbext{deprecated}
|
||||
|
||||
The @code{sb-ext:deprecated} declaration can be used to declare objects
|
||||
in various namespaces@footnote{See ``namespace'' entry in the glossary
|
||||
of the Common Lisp Hyperspec.} as deprecated.
|
||||
in various namespaces as deprecated.
|
||||
|
||||
@deffn {Declaration} @sbext{deprecated}
|
||||
@quotation
|
||||
@emph{Note}: See the @code{namespace} @code{clhs} glossary entry in the glossary of
|
||||
the Common Lisp Hyperspec.)
|
||||
@end quotation
|
||||
|
||||
Syntax:
|
||||
@example
|
||||
@code{sb-ext:deprecated} stage since @{object-clause@}*
|
||||
@itemize
|
||||
@item [@strong{declaration}] @code{sb-ext:deprecated}
|
||||
|
||||
stage ::= @{:early | :late | :final@}
|
||||
Syntax: @code{(sb-ext:deprecated stage since &rest object-clauses)}
|
||||
|
||||
since ::= @{@var{version} | (@var{software} @var{version})@}
|
||||
stage ::= @{@code{:early} | @code{:late} | @code{:final}@}
|
||||
|
||||
object-clause ::= (namespace @var{name} [:replacement @var{replacement}])
|
||||
since ::= @{@code{<version>} | (@code{<software>} @code{<version>})@}
|
||||
|
||||
namespace ::= @{cl:variable | cl:function | cl:type@}
|
||||
@end example
|
||||
object-clause ::= (namespace @code{<name>} [@code{:replacement} @code{<replacement>}])
|
||||
|
||||
@noindent were @var{name} is the name of the deprecated thing,
|
||||
@var{version} and @var{software} are strings describing the version in
|
||||
which the thing has been deprecated and @var{replacement} is a name or a
|
||||
list of names designating things that should be used instead of the
|
||||
deprecated thing.
|
||||
namespace ::= @{@code{cl:variable} | @code{cl:function} | @code{cl:type}@}
|
||||
|
||||
where the terminal @code{<name>} is the name of the deprecated thing,
|
||||
@code{<version>} and @code{<software>} are strings describing the version
|
||||
in which the thing has been deprecated and @code{<replacement>} is a
|
||||
name or a list of names designating things that should be used
|
||||
instead of the deprecated thing.
|
||||
|
||||
Currently the following namespaces are supported:
|
||||
|
||||
@table @code
|
||||
@itemize
|
||||
@item @code{cl:function}: Declare functions, compiler-macros or macros as
|
||||
deprecated.
|
||||
|
||||
@item cl:function
|
||||
Declare functions, compiler-macros or macros as deprecated.
|
||||
|
||||
@quotation note
|
||||
When declaring a function to be in @code{:final} deprecation, there
|
||||
should be no actual definition of the function as the declaration emits
|
||||
a stub function that signals a
|
||||
@tindex @sbext{deprecation-error}
|
||||
should be no actual definition of the function as the
|
||||
declaration emits a stub function that signals a
|
||||
@code{sb-ext:deprecation-error} at run-time when called.
|
||||
@end quotation
|
||||
|
||||
@item cl:variable
|
||||
Declare special and global variables, constants and symbol-macros as
|
||||
deprecated.
|
||||
@item @code{cl:variable}: Declare special and global variables, constants
|
||||
and symbol-macros as deprecated.
|
||||
|
||||
@quotation note
|
||||
When declaring a variable to be in @code{:final} deprecation, there
|
||||
should be no actual definition of the variable as the declaration emits
|
||||
a symbol-macro that signals a
|
||||
@tindex @sbext{deprecation-error}
|
||||
should be no actual definition of the variable as the
|
||||
declaration emits a symbol-macro that signals a
|
||||
@code{sb-ext:deprecation-error} at run-time when accessed.
|
||||
@end quotation
|
||||
|
||||
@item cl:type
|
||||
Declare named types (i.e. defined via @code{deftype}), standard classes,
|
||||
structure classes and condition classes as deprecated.
|
||||
@item @code{cl:type}: Declare named types (i.e. defined via @code{deftype}),
|
||||
standard classes, structure classes and condition classes as
|
||||
deprecated.
|
||||
@end itemize
|
||||
@end itemize
|
||||
|
||||
@end table
|
||||
@end deffn
|
||||
|
||||
@node Deprecation Examples
|
||||
@comment node-name, next, previous, up
|
||||
@node deprecation examples
|
||||
@section Deprecation Examples
|
||||
@cindex Deprecation Examples
|
||||
|
||||
Marking functions as deprecated:
|
||||
@lisp
|
||||
|
||||
@example
|
||||
(defun foo ())
|
||||
(defun bar ())
|
||||
(declaim (deprecated :early ("my-system" "1.2.3")
|
||||
|
|
@ -283,10 +276,11 @@ Marking functions as deprecated:
|
|||
;; :final deprecation:
|
||||
(declaim (deprecated :final ("my-system" "1.2.3")
|
||||
(function fez :replacement whoop)))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
@noindent Attempting to use the deprecated functions:
|
||||
@lisp
|
||||
Attempting to use the deprecated functions:
|
||||
|
||||
@example
|
||||
(defun baz ()
|
||||
(foo))
|
||||
| STYLE-WARNING: The function CL-USER::FOO has been deprecated...
|
||||
|
|
@ -300,69 +294,75 @@ Marking functions as deprecated:
|
|||
=> DANGER
|
||||
(danger)
|
||||
|- ERROR: The function CL-USER::FEZ has been deprecated...
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
@node Deprecated Interfaces in SBCL
|
||||
@comment node-name, next, previous, up
|
||||
@node deprecated interfaces in sbcl
|
||||
@section Deprecated Interfaces in SBCL
|
||||
|
||||
@menu
|
||||
* List of Deprecated Interfaces: list of deprecated interfaces.
|
||||
* Historical Interfaces: historical interfaces.
|
||||
@end menu
|
||||
|
||||
This sections lists legacy interfaces in various stages of deprecation.
|
||||
|
||||
@node list of deprecated interfaces
|
||||
@subsection List of Deprecated Interfaces
|
||||
|
||||
@menu
|
||||
* Early Deprecation: early deprecation.
|
||||
* Late Deprecation: late deprecation.
|
||||
* Final Deprecation: final deprecation.
|
||||
@end menu
|
||||
|
||||
@node early deprecation
|
||||
@subsubsection Early Deprecation
|
||||
|
||||
@tindex @sbext{early-deprecation-warning}
|
||||
|
||||
@itemize
|
||||
|
||||
@item @strong{SOCKINT::WIN32-*}
|
||||
@item @code{sockint::win32-*}
|
||||
|
||||
Deprecated in favor of the corresponding prefix-less functions
|
||||
(e.g. @code{sockint::bind} replaces @code{sockint::win32-bind}) as of
|
||||
1.2.10 in March 2015. Expected to move into late deprecation in August
|
||||
2015.
|
||||
1.2.10 in March 2015. Expected to move into late deprecation in
|
||||
August 2015.
|
||||
|
||||
@sp 1
|
||||
@item @strong{SB-UNIX:UNIX-EXIT}
|
||||
@item @code{sb-unix:unix-exit}
|
||||
|
||||
Deprecated as of 1.0.56.55 in May 2012. Expected to move into late
|
||||
deprecation in May 2013.
|
||||
Deprecated as of 1.0.56.55 in May 2012. Expected to move into
|
||||
late deprecation in May 2013.
|
||||
|
||||
When the SBCL process termination was refactored as part of changes that
|
||||
led to @code{sb-ext:quit} being deprecated, @code{sb-unix:unix-exit}
|
||||
ceased to be used internally. Since @code{SB-UNIX} is an internal package
|
||||
not intended for user code to use, and since we're slowly in the process
|
||||
of refactoring things to be less Unix-oriented, @code{sb-unix:unix-exit}
|
||||
was initially deleted as it was no longer used. Unfortunately it became
|
||||
apparent that it was used by several external users, so it was re-instated
|
||||
in deprecated form.
|
||||
When the SBCL process termination was refactored,
|
||||
@code{sb-unix:unix-exit} ceased to be used internally. Since @code{sb-unix}
|
||||
is an internal package not intended for user code to use, and
|
||||
since we're slowly in the process of refactoring things to be
|
||||
less Unix-oriented, @code{sb-unix:unix-exit} was initially deleted as
|
||||
it was no longer used. Unfortunately it became apparent that it
|
||||
was used by several external users, so it was re-instated in
|
||||
deprecated form.
|
||||
|
||||
While the cost of keeping @code{sb-unix:unix-exit} indefinitely is
|
||||
trivial, the ability to refactor our internals is important, so its
|
||||
deprecation was taken as an opportunity to highlight that
|
||||
@code{SB-UNIX} is an internal package and @code{SB-POSIX} should be
|
||||
used by user-programs instead -- or alternatively calling the foreign
|
||||
function directly if the desired interface doesn't for some reason
|
||||
exist in @code{SB-POSIX}.
|
||||
trivial, the ability to refactor our internals is important, so
|
||||
its deprecation was taken as an opportunity to highlight that
|
||||
@code{sb-unix} is an internal package and @code{sb-posix} should be used
|
||||
by user-programs instead -- or alternatively calling the foreign
|
||||
function directly if the desired interface doesn't for some
|
||||
reason exist in @code{sb-posix}.
|
||||
|
||||
@strong{Remedy}
|
||||
|
||||
For code needing to work with legacy SBCLs, use e.g. @code{system-exit}
|
||||
as show above in remedies for @code{sb-ext:quit}. In modern SBCLs
|
||||
simply call either @code{sb-posix:exit} or @code{sb-ext:exit} with
|
||||
appropriate arguments.
|
||||
For code needing to work with legacy SBCLs, use e.g.
|
||||
@code{system-exit}. In modern SBCLs, simply call either @code{sb-posix:exit}
|
||||
or @code{sb-ext:exit} with appropriate arguments.
|
||||
|
||||
@sp 1
|
||||
@item @strong{SB-C::MERGE-TAIL-CALLS Compiler Policy}
|
||||
@item @code{sb-c::merge-tail-calls} compiler policy
|
||||
|
||||
Deprecated as of 1.0.53.74 in November 2011. Expected to move into
|
||||
late deprecation in November 2012.
|
||||
Deprecated as of 1.0.53.74 in November 2011. Expected to move
|
||||
into late deprecation in November 2012.
|
||||
|
||||
This compiler policy was never functional: SBCL has always merged tail
|
||||
calls when it could, regardless of this policy setting. (It was also
|
||||
never officially supported, but several code-bases have historically
|
||||
used it.)
|
||||
This compiler policy was never functional: SBCL has always
|
||||
merged tail calls when it could, regardless of this policy
|
||||
setting. (It was also never officially supported, but several
|
||||
code-bases have historically used it.)
|
||||
|
||||
@strong{Remedy}
|
||||
|
||||
|
|
@ -370,52 +370,49 @@ Simply remove the policy declarations. They were never necessary: SBCL
|
|||
always merged tail-calls when possible. To disable tail merging,
|
||||
structure the code to avoid the tail position instead.
|
||||
|
||||
@sp 1
|
||||
@item @strong{Spinlock API}
|
||||
@item The Spinlock API
|
||||
|
||||
Deprecated as of 1.0.53.11 in August 2011. Expected to move into late
|
||||
deprecation in August 2012.
|
||||
Deprecated as of 1.0.53.11 in August 2011. Expected to move into
|
||||
late deprecation in August 2012.
|
||||
|
||||
Spinlocks were an internal interface, but had a number of external users
|
||||
and were hence deprecated instead of being simply deleted.
|
||||
Spinlocks were an internal interface but had a number of
|
||||
external users and were hence deprecated instead of being simply
|
||||
deleted.
|
||||
|
||||
Affected symbols: @code{sb-thread::spinlock},
|
||||
@code{sb-thread::make-spinlock}, @code{sb-thread::with-spinlock},
|
||||
@code{sb-thread::with-recursive-spinlock},
|
||||
Affected symbols: @code{sb-thread::spinlock}, @code{sb-thread::make-spinlock},
|
||||
@code{sb-thread::with-spinlock}, @code{sb-thread::with-recursive-spinlock},
|
||||
@code{sb-thread::get-spinlock}, @code{sb-thread::release-spinlock},
|
||||
@code{sb-thread::spinlock-value}, and @code{sb-thread::spinlock-name}.
|
||||
|
||||
@strong{Remedy}
|
||||
|
||||
Use the mutex API instead, or implement spinlocks suiting your needs
|
||||
on top of @code{sb-ext:compare-and-swap},
|
||||
@code{sb-ext:spin-loop-hint}, etc.
|
||||
Use the mutex API instead, or implement spinlocks suiting your
|
||||
needs on top of @code{sb-ext:compare-and-swap}, @code{sb-ext:spin-loop-hint},
|
||||
etc.
|
||||
|
||||
@item @strong{SOCKINT::HANDLE->FD}, @strong{SOCKINT::FD->HANDLE}
|
||||
|
||||
Internally deprecated in 2012. Declared deprecated as of 1.2.10 in March
|
||||
2015. Expected to move into final deprecation in August 2015.
|
||||
@item @code{sockint::handle->fd}, @code{sockint::fd->handle}
|
||||
|
||||
Internally deprecated in 2012. Declared deprecated as of 1.2.10
|
||||
in March 2015. Expected to move into final deprecation in August
|
||||
2015.
|
||||
@end itemize
|
||||
|
||||
@node late deprecation
|
||||
@subsubsection Late Deprecation
|
||||
|
||||
@tindex @sbext{late-deprecation-warning}
|
||||
|
||||
@itemize
|
||||
|
||||
@item @strong{SB-THREAD:JOIN-THREAD-ERROR-THREAD and SB-THREAD:INTERRUPT-THREAD-ERROR-THREAD}
|
||||
@item @code{sb-thread:join-thread-error-thread} and
|
||||
@code{sb-thread:interrupt-thread-error-thread}
|
||||
|
||||
Deprecated in favor of @code{sb-thread:thread-error-thread} as of
|
||||
1.0.29.17 in June 2009. Expected to move into final deprecation in
|
||||
June 2012.
|
||||
1.0.29.17 in June 2009. Expected to move into final deprecation
|
||||
in June 2012.
|
||||
|
||||
@strong{Remedy}
|
||||
|
||||
For code that needs to support legacy SBCLs, use e.g.:
|
||||
|
||||
@sp 1
|
||||
@lisp
|
||||
@example
|
||||
(defun get-thread-error-thread (condition)
|
||||
#+#.(cl:if (cl:find-symbol "THREAD-ERROR-THREAD" :sb-thread)
|
||||
'(and) '(or))
|
||||
|
|
@ -427,25 +424,22 @@ For code that needs to support legacy SBCLs, use e.g.:
|
|||
(sb-thread:join-thread-error-thread condition))
|
||||
(sb-thread:interrupt-thread-error
|
||||
(sb-thread:interrupt-thread-error-thread condition))))
|
||||
@end lisp
|
||||
@sp 1
|
||||
@end example
|
||||
|
||||
@sp 1
|
||||
@item @strong{SB-INTROSPECT:FUNCTION-ARGLIST}
|
||||
@item @code{sb-introspect:function-arglist}
|
||||
|
||||
Deprecated in favor of @code{sb-introspect:function-lambda-list} as of
|
||||
1.0.24.5 in January 2009. Expected to move into final deprecation in
|
||||
January 2012.
|
||||
1.0.24.5 in January 2009. Expected to move into final
|
||||
deprecation in January 2012.
|
||||
|
||||
Renamed for consistency and aesthetics. Functions have lambda-lists,
|
||||
not arglists.
|
||||
Renamed for consistency and aesthetics. Functions have
|
||||
lambda-lists, not arglists.
|
||||
|
||||
@strong{Remedy}
|
||||
|
||||
@example
|
||||
For code that needs to support legacy SBCLs, use e.g.:
|
||||
|
||||
@sp 1
|
||||
@lisp
|
||||
(defun get-function-lambda-list (function)
|
||||
#+#.(cl:if (cl:find-symbol "FUNCTION-LAMBDA-LIST" :sb-introspect)
|
||||
'(and) '(or))
|
||||
|
|
@ -453,43 +447,38 @@ For code that needs to support legacy SBCLs, use e.g.:
|
|||
#-#.(cl:if (cl:find-symbol "FUNCTION-LAMBDA-LIST" :sb-introspect)
|
||||
'(and) '(or))
|
||||
(sb-introspect:function-arglist function))
|
||||
@end lisp
|
||||
@sp 1
|
||||
@end example
|
||||
|
||||
@sp 1
|
||||
@item @strong{Stack Allocation Policies}
|
||||
@item Stack Allocation Policies
|
||||
|
||||
Deprecated in favor of @code{sb-ext:*stack-allocate-dynamic-extent*}
|
||||
as of 1.0.19.7 in August 2008, and are expected to be removed in
|
||||
Deprecated in favor of @code{sb-ext:*stack-allocate-dynamic-extent*} as
|
||||
of 1.0.19.7 in August 2008, and are expected to be removed in
|
||||
August 2012.
|
||||
|
||||
Affected symbols: @code{sb-c::stack-allocate-dynamic-extent},
|
||||
@code{sb-c::stack-allocate-vector}, and
|
||||
@code{sb-c::stack-allocate-value-cells}.
|
||||
|
||||
These compiler policies were never officially supported, and turned
|
||||
out the be a flawed design.
|
||||
These compiler policies were never officially supported, and
|
||||
turned out the be a flawed design.
|
||||
|
||||
@strong{Remedy}
|
||||
|
||||
For code that needs stack-allocation in legacy SBCLs, conditionalize
|
||||
using:
|
||||
For code that needs stack-allocation in legacy SBCLs,
|
||||
conditionalize using:
|
||||
|
||||
@sp 1
|
||||
@lisp
|
||||
@example
|
||||
#-#.(cl:if (cl:find-symbol "*STACK-ALLOCATE-DYNAMIC-EXTENT*" :sb-ext)
|
||||
'(and) '(or))
|
||||
(declare (optimize sb-c::stack-allocate-dynamic-extent))
|
||||
@end lisp
|
||||
@sp 1
|
||||
@end example
|
||||
|
||||
However, unless stack allocation is essential, we recommend simply
|
||||
removing these declarations. Refer to documentation on
|
||||
@code{sb-ext:*stack-allocate-dynamic*} for details on stack allocation
|
||||
control in modern SBCLs.
|
||||
However, unless stack allocation is essential, we recommend
|
||||
simply removing these declarations. Refer to documentation on
|
||||
@code{sb-ext:*stack-allocate-dynamic*} for details on stack
|
||||
allocation control in modern SBCLs.
|
||||
|
||||
@sp 1
|
||||
@item @strong{SB-SYS:OUTPUT-RAW-BYTES}
|
||||
@item @code{sb-sys:output-raw-bytes}
|
||||
|
||||
Deprecated as of 1.0.8.16 in June 2007. Expected to move into final
|
||||
deprecation in June 2012.
|
||||
|
|
@ -500,39 +489,36 @@ bivalent streams.
|
|||
|
||||
@strong{Remedy}
|
||||
|
||||
Use streams with element-type @code{(unsigned-byte 8)}
|
||||
or @code{:default} -- the latter allowing both binary and
|
||||
character IO -- in conjunction with @code{write-sequence}.
|
||||
|
||||
Use streams with element-type (@code{unsigned-byte} 8) or
|
||||
@code{:default} -- the latter allowing both binary and character IO --
|
||||
in conjunction with @code{write-sequence}.
|
||||
@end itemize
|
||||
|
||||
@node final deprecation
|
||||
@subsubsection Final Deprecation
|
||||
|
||||
@tindex @sbext{final-deprecation-warning}
|
||||
|
||||
No interfaces are currently in final deprecation.
|
||||
|
||||
@node historical interfaces
|
||||
@subsection Historical Interfaces
|
||||
|
||||
The following is a partial list of interfaces present in historical
|
||||
versions of SBCL, which have since then been deleted.
|
||||
|
||||
@itemize
|
||||
@item @code{sb-kernel:instance-lambda}
|
||||
|
||||
@item @strong{SB-KERNEL:INSTANCE-LAMBDA}
|
||||
Historically needed for CLOS code. Deprecated as of 0.9.3.32 in
|
||||
August 2005. Deleted as of 1.0.47.8 in April 2011. Plain @code{lambda}
|
||||
can be used where SB-KERNEL:INSTANCE-LAMBDA used to be needed.
|
||||
|
||||
Historically needed for CLOS code. Deprecated as of 0.9.3.32 in August
|
||||
2005. Deleted as of 1.0.47.8 in April 2011. Plain @code{lambda} can be
|
||||
used where @code{sb-kernel:instance-lambda} used to be needed.
|
||||
|
||||
@sp 1
|
||||
@item @strong{SB-ALIEN:DEF-ALIEN-ROUTINE, SB-ALIEN:DEF-ALIEN-VARIABLE, SB-ALIEN:DEF-ALIEN-TYPE}
|
||||
|
||||
Inherited from CMUCL, naming convention not consistent with preferred
|
||||
SBCL style. Deprecated as of 0.pre7.90 in December 2001. Deleted as of
|
||||
1.0.9.17 in September 2007. Replaced by
|
||||
@code{sb-alien:define-alien-routine},
|
||||
@code{sb-alien:define-alien-variable}, and
|
||||
@code{sb-alien:define-alien-type}.
|
||||
@item @code{sb-alien:def-alien-routine}, @code{sb-alien:def-alien-variable},
|
||||
@code{sb-alien:def-alien-type}
|
||||
|
||||
Inherited from CMUCL, naming convention not consistent with
|
||||
preferred SBCL style. Deprecated as of 0.pre7.90 in December
|
||||
2001. Deleted as of 1.0.9.17 in September 2007. Replaced by
|
||||
@code{sb-alien:define-alien-routine}, @code{sb-alien:define-alien-variable},
|
||||
and @code{sb-alien:define-alien-type}.
|
||||
@end itemize
|
||||
|
||||
|
|
|
|||
|
|
@ -1,46 +1,52 @@
|
|||
@node Efficiency
|
||||
@comment node-name, next, previous, up
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node efficiency
|
||||
@chapter Efficiency
|
||||
@cindex Efficiency
|
||||
|
||||
@menu
|
||||
* Slot access::
|
||||
* Stack allocation::
|
||||
* Modular arithmetic::
|
||||
* Recognized idioms::
|
||||
* Global and Always-Bound variables::
|
||||
* Miscellaneous Efficiency Issues::
|
||||
* Slot Access: slot access.
|
||||
* Stack Allocation: stack allocation.
|
||||
* Modular Arithmetic: modular arithmetic.
|
||||
* Recognized Idioms: recognized idioms.
|
||||
* Global and Always-bound Variables: global and always bound variables.
|
||||
* Miscellaneous Efficiency Issues: miscellaneous efficiency issues.
|
||||
@end menu
|
||||
|
||||
@node Slot access
|
||||
@comment node-name, next, previous, up
|
||||
@section Slot access
|
||||
@cindex Slot access
|
||||
@node slot access
|
||||
@section Slot Access
|
||||
|
||||
@subsection Structure object slot access
|
||||
@menu
|
||||
* Structure Object Slot Access: structure object slot access.
|
||||
* Standard Object Slot Access: standard object slot access.
|
||||
@end menu
|
||||
|
||||
Structure slot accessors are efficient only if the compiler is able to
|
||||
open code them: compiling a call to a structure slot accessor before
|
||||
the structure is defined, declaring one @code{notinline}, or passing
|
||||
it as a functional argument to another function causes severe
|
||||
performance degradation.
|
||||
@node structure object slot access
|
||||
@subsection Structure Object Slot Access
|
||||
|
||||
@subsection Standard object slot access
|
||||
Structure slot accessors are efficient only if the compiler is
|
||||
able to open code them: compiling a call to a structure slot
|
||||
accessor before the structure is defined, declaring one @code{notinline},
|
||||
or passing it as a functional argument to another function causes
|
||||
severe performance degradation.
|
||||
|
||||
@node standard object slot access
|
||||
@subsection Standard Object Slot Access
|
||||
|
||||
The most efficient way to access a slot of a @code{standard-object} is
|
||||
by using @code{slot-value} with a constant slot name argument inside a
|
||||
@code{defmethod} body, where the variable holding the instance is a
|
||||
specializer parameter of the method and is never assigned to. The cost
|
||||
is roughly 1.6 times that of an open coded structure slot accessor.
|
||||
specializer parameter of the method and is never assigned to. The
|
||||
cost is roughly 1.6 times that of an open coded structure slot
|
||||
accessor.
|
||||
|
||||
Second most efficient way is to use a CLOS slot accessor, or
|
||||
@code{slot-value} with a constant slot name argument, but in
|
||||
circumstances other than specified above. This may be up to 3 times as
|
||||
slow as the method described above.
|
||||
@code{slot-value} with a constant slot name argument, but in circumstances
|
||||
other than specified above. This may be up to 3 times as slow as the
|
||||
method described above.
|
||||
|
||||
Example:
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(defclass foo () ((bar)))
|
||||
|
||||
;; Fast: specializer and never assigned to
|
||||
|
|
@ -62,96 +68,81 @@ Example:
|
|||
(setf (slot-value foo 'bar) new)
|
||||
(setf foo new)
|
||||
old))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
Note that when profiling code such as this, the first few calls to the
|
||||
generic function are not representative, as the dispatch mechanism is
|
||||
lazily set up during those calls.
|
||||
|
||||
@node Stack allocation
|
||||
@comment node-name, next, previous, up
|
||||
@section Stack allocation
|
||||
@cindex @code{dynamic-extent} declaration
|
||||
@cindex declaration, @code{dynamic-extent}
|
||||
@node stack allocation
|
||||
@section Stack Allocation
|
||||
|
||||
SBCL has fairly extensive support for performing allocations on the
|
||||
stack when a variable or function is declared @code{dynamic-extent}. The
|
||||
@code{dynamic-extent} declarations are not verified, but are simply
|
||||
trusted as long as @code{sb-ext:*stack-allocate-dynamic-extent*} is
|
||||
true.
|
||||
@code{dynamic-extent} declarations are not verified but are simply trusted
|
||||
as long as @code{sb-ext:*stack-allocate-dynamic-extent*} is true.
|
||||
|
||||
@include var-sb-ext-star-stack-allocate-dynamic-extent-star.texinfo
|
||||
@anchor{Variable sb-ext *stack-allocate-dynamic-extent*}
|
||||
@vvindex @sortas{stack-allocate-dynamic-extent* sb-ext} *stack-allocate-dynamic-extent* [sb-ext]
|
||||
@deffn{Variable} sb-ext:*stack-allocate-dynamic-extent*
|
||||
If true (the default), the compiler believes @code{dynamic-extent} declarations
|
||||
and stack allocates otherwise inaccessible parts of the object whenever
|
||||
possible.
|
||||
@end deffn
|
||||
SBCL recognizes any value which a variable declared @code{dynamic-extent}
|
||||
can take on as having dynamic extent. This means that, in addition
|
||||
to the value a variable is bound to initially, a value assigned to a
|
||||
variable by @code{setq} is also recognized as having dynamic extent when
|
||||
the variable is declared @code{dynamic-extent}. Users can thus build
|
||||
complex structures on the stack using iteration and @code{setq}.
|
||||
|
||||
SBCL recognizes any value which a variable declared
|
||||
@code{dynamic-extent} can take on as having dynamic extent. This means
|
||||
that, in addition to the value a variable is bound to initially, a value
|
||||
assigned to a variable by @code{setq} is also recognized as having
|
||||
dynamic extent when the variable is declared
|
||||
@code{dynamic-extent}. Users can thus build complex structures on the
|
||||
stack using iteration and @code{setq}.
|
||||
|
||||
At present, SBCL implements stack allocation for the following kinds of
|
||||
values when they are recognized as having dynamic extent:
|
||||
At present, SBCL implements stack allocation for the following kinds
|
||||
of values when they are recognized as having dynamic extent:
|
||||
|
||||
@itemize
|
||||
@item @code{&rest} lists;
|
||||
|
||||
@item
|
||||
@code{&rest} lists
|
||||
@item the results of @code{cons}, @code{list}, @code{list*}, and @code{vector};
|
||||
|
||||
@item
|
||||
@findex @cl{cons}
|
||||
@findex @cl{list}
|
||||
@findex @cl{list*}
|
||||
@findex @cl{vector}
|
||||
the results of @code{cons}, @code{list}, @code{list*}, and @code{vector}
|
||||
@item the result of simple forms of @code{make-array}: stack allocation is
|
||||
possible only if the resulting array is known to be both simple
|
||||
and one-dimensional, and has a constant @code{:element-type};
|
||||
|
||||
@item
|
||||
@findex @cl{make-array}
|
||||
the result of simple forms of @code{make-array}: stack allocation is
|
||||
possible only if the resulting array is known to be both simple and
|
||||
one-dimensional, and has a constant @code{:element-type}.
|
||||
@quotation
|
||||
@strong{Warning}: Stack space is limited, so allocation of a large
|
||||
vector may cause stack overflow. Stack overflow checks are
|
||||
done except in zero @code{safety} policies.
|
||||
@end quotation
|
||||
|
||||
@cindex Safety optimization quality
|
||||
@strong{Note}: stack space is limited, so allocation of a large vector
|
||||
may cause stack overflow. Stack overflow checks are done except in zero
|
||||
@code{safety} policies.
|
||||
@item closures defined with @code{flet} or @code{labels} with a bound @code{dynamic-extent}
|
||||
declaration;
|
||||
|
||||
@item
|
||||
@findex @cl{flet}
|
||||
@findex @cl{labels}
|
||||
@cindex @code{safety} optimization quality
|
||||
@cindex optimization quality, @code{safety}
|
||||
closures defined with @code{flet} or @code{labels} with a bound
|
||||
@code{dynamic-extent} declaration.
|
||||
@item anonymous closures defined with @code{lambda};
|
||||
|
||||
@item
|
||||
anonymous closures defined with @code{lambda}
|
||||
@item user-defined structures when the structure constructor defined using
|
||||
@code{defstruct} has been declared @code{inline};
|
||||
|
||||
@item
|
||||
user-defined structures when the structure constructor defined using
|
||||
@code{defstruct} has been declared @code{inline}
|
||||
|
||||
@strong{Note}: structures with ``raw'' slots can currently be
|
||||
stack-allocated only on x86 and x86-64. A ``raw'' slot is one whose
|
||||
declared type is a subtype of exactly one of: @code{double-float},
|
||||
@code{single-float}, @code{(complex double-float)}, @code{(complex single-float)},
|
||||
or @code{sb-ext:word}; but as an exception to the preceding, any subtype
|
||||
of @code{fixnum} is not stored as raw despite also being a subtype
|
||||
of @code{sb-ext:word}.
|
||||
|
||||
@item
|
||||
otherwise-inaccessible parts of objects recognized to be dynamic
|
||||
extent. The support for detecting when this applies is very
|
||||
sophisticated. The compiler can do this detection when any value form
|
||||
for a variable contains conditional allocations, function calls, inlined
|
||||
functions, anonymous closures, or even other variables. This allows
|
||||
stack allocation of complex structures.
|
||||
@quotation
|
||||
@emph{Note}: Structures with @emph{raw} slots can currently be
|
||||
stack-allocated only on x86 and x86-64. A raw slot is one
|
||||
whose declared type is a subtype of exactly one of:
|
||||
@code{double-float}, @code{single-float}, @code{(complex
|
||||
double-float)}, @code{(complex single-float)}, or @code{sb-ext:word}; but
|
||||
as an exception to the preceding, any subtype of @code{fixnum} is not
|
||||
stored as raw despite also being a subtype of @code{sb-ext:word}.
|
||||
@end quotation
|
||||
|
||||
@item otherwise-inaccessible parts of objects recognized to be dynamic
|
||||
extent. The support for detecting when this applies is very
|
||||
sophisticated. The compiler can do this detection when any value
|
||||
form for a variable contains conditional allocations, function
|
||||
calls, inlined functions, anonymous closures, or even other
|
||||
variables. This allows stack allocation of complex structures.
|
||||
@end itemize
|
||||
|
||||
Examples:
|
||||
|
||||
@lisp
|
||||
@example
|
||||
;;; Declaiming a structure constructor inline before definition makes
|
||||
;;; stack allocation possible.
|
||||
(declaim (inline make-thing))
|
||||
|
|
@ -190,38 +181,40 @@ Examples:
|
|||
(defun foo (&rest args)
|
||||
(declare (dynamic-extent args))
|
||||
...)
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
As a notable exception to recognizing otherwise inaccessible parts of
|
||||
other recognized dynamic extent values, SBCL does not as of 1.0.48.21
|
||||
propagate dynamic-extentness through @code{&rest} arguments -- but
|
||||
another conforming implementation might, so portable code should not
|
||||
rely on this.
|
||||
As a notable exception to recognizing otherwise inaccessible parts
|
||||
of other recognized dynamic extent values, SBCL does not as of
|
||||
1.0.48.21 propagate dynamic-extentness through @code{&rest} arguments --
|
||||
but another conforming implementation might, so portable code should
|
||||
not rely on this.
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(declaim (inline foo))
|
||||
(defun foo (fun &rest arguments)
|
||||
(declare (dynamic-extent arguments))
|
||||
(apply fun arguments))
|
||||
|
||||
(defun bar (a)
|
||||
;; SBCL will heap allocate the result of (LIST A), and stack allocate
|
||||
;; only the spine of the &rest list -- so this is safe, but unportable.
|
||||
;; SBCL will heap allocate the result of (LIST A), and stack
|
||||
;; allocate only the spine of the &rest list -- so this is
|
||||
;; safe but unportable.
|
||||
;;
|
||||
;; Another implementation, including earlier versions of SBCL might consider
|
||||
;; (LIST A) to be otherwise inaccessible and stack-allocate it as well!
|
||||
;; Another implementation, including earlier versions of SBCL
|
||||
;; might consider (LIST A) to be otherwise inaccessible and
|
||||
;; stack-allocate it as well!
|
||||
(foo #'car (list a)))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
If dynamic extent constraints specified in the Common Lisp standard
|
||||
are violated, the best that can happen is for the program to have
|
||||
garbage in variables and return values; more commonly, the system will
|
||||
crash.
|
||||
garbage in variables and return values; more commonly, the system
|
||||
will crash.
|
||||
|
||||
In particular, it is important to realize that this can interact in
|
||||
suprising ways with the otherwise inaccessible parts criterion:
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(let* ((a (list 1 2 3))
|
||||
(b (cons a a)))
|
||||
(declare (dynamic-extent b))
|
||||
|
|
@ -231,18 +224,18 @@ suprising ways with the otherwise inaccessible parts criterion:
|
|||
;;
|
||||
;; Hence returning (CAR B) here is unsafe.
|
||||
...)
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
SBCL also performs sophisticated escape analysis to enable automatic
|
||||
stack allocation of local functions without any bound dynamic extent
|
||||
declarations in many situations where the compiler can prove that no
|
||||
uses escape (traditional Lisp terminology names this situation ``all
|
||||
uses are downward funargs''). For example, in the following function,
|
||||
the local function @code{#'predicatep} is stack allocated, because the
|
||||
compiler understands that the built-in function @code{#'position-if}
|
||||
only uses its first argument as a downward funarg:
|
||||
uses escape (traditional Lisp terminology names this situation "all
|
||||
uses are downward funargs"). For example, in the following
|
||||
function, the local function @code{#'predicatep} is stack allocated,
|
||||
because the compiler understands that the built-in function
|
||||
@code{position-if} only uses its first argument as a downward funarg:
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(let ((acc 0))
|
||||
(flet ((predicatep (num) (plusp (+ num off))))
|
||||
(dotimes (i 10)
|
||||
|
|
@ -251,139 +244,150 @@ only uses its first argument as a downward funarg:
|
|||
(incf acc (if (positivep acc) 10 3))
|
||||
(incf acc (position-if #'predicatep array))))
|
||||
acc)
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
Users can also declare that their own functions take downward funargs by
|
||||
adding bound dynamic extent declarations on the function arguments.
|
||||
Users can also declare that their own functions take downward
|
||||
funargs by adding bound dynamic extent declarations on the function
|
||||
arguments.
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(defun trivial-hof (fun arg)
|
||||
(declare (dynamic-extent fun))
|
||||
(funcall fun 3 arg))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
Currently, such dynamic extent declarations only cause stack allocation
|
||||
of downward funargs at call sites on sufficiently unsafe policy. This is
|
||||
partly because the compiler is currently not able to detect incorrect
|
||||
usage of dynamic extent declarations.
|
||||
Currently, such dynamic extent declarations only cause stack
|
||||
allocation of downward funargs at call sites on sufficiently unsafe
|
||||
policy. This is partly because the compiler is currently not able to
|
||||
detect incorrect usage of dynamic extent declarations.
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(defun autodxclosure1 (&optional (x 4))
|
||||
;; Calling a higher-order function will only implicitly
|
||||
;; stack-allocate a funarg if the callee is trusted (a CL: function)
|
||||
;; or the caller is unsafe.
|
||||
;; stack-allocate a funarg if the callee is trusted (a CL:
|
||||
;; function) or the caller is unsafe.
|
||||
(declare (optimize speed (safety 0) (debug 0)))
|
||||
(trivial-hof (lambda (a b) (+ a b x)) 92))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
@node Modular arithmetic
|
||||
@comment node-name, next, previous, up
|
||||
@section Modular arithmetic
|
||||
@cindex Modular arithmetic
|
||||
@cindex Arithmetic, modular
|
||||
@cindex Arithmetic, hardware
|
||||
@findex @cl{logand}
|
||||
Some numeric functions have a property: @var{N} lower bits of the
|
||||
result depend only on @var{N} lower bits of (all or some)
|
||||
arguments. If the compiler sees an expression of form @code{(logand
|
||||
@var{exp} @var{mask})}, where @var{exp} is a tree of such ``good''
|
||||
functions and @var{mask} is known to be of type @code{(unsigned-byte
|
||||
@var{w})}, where @var{w} is a ``good'' width, all intermediate results
|
||||
will be cut to @var{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.
|
||||
@node modular arithmetic
|
||||
@section Modular Arithmetic
|
||||
|
||||
Consider an example.
|
||||
@menu
|
||||
* Signed Modular Arithmetic: signed modular arithmetic.
|
||||
@end menu
|
||||
|
||||
@lisp
|
||||
Some numeric functions have a property: n lower bits of the
|
||||
result depend only on n lower bits of (all or some) arguments. If
|
||||
the compiler sees an expression of form @code{(logand <expr> <mask>)},
|
||||
where @code{<expr>} is a tree of such @emph{good} functions and @code{<mask>} is
|
||||
known to be of type @code{(unsigned-byte <w>)}, where @code{<w>} is a @emph{good}
|
||||
width, all intermediate results will be cut to @code{<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.
|
||||
|
||||
Consider this example:
|
||||
|
||||
@example
|
||||
(defun i (x y)
|
||||
(declare (type (unsigned-byte 32) x y))
|
||||
(ldb (byte 32 0) (logxor x (lognot y))))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
The result of @code{(lognot y)} will be negative and of type
|
||||
@code{(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 @code{logxor} and @code{lognot}
|
||||
with versions cutting results to 32 bits, and because terminals
|
||||
(here---expressions @code{x} and @code{y}) are also of type
|
||||
@code{(unsigned-byte 32)}, 32-bit machine arithmetic can be used.
|
||||
@code{(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 @code{logxor} and @code{lognot} with versions
|
||||
cutting results to 32 bits, and because terminals (here, expressions
|
||||
@code{x} and @code{y}) are also of type @code{(unsigned-byte 32)}, 32-bit machine
|
||||
arithmetic can be used.
|
||||
|
||||
As of SBCL 0.8.5 ``good'' functions are @code{+}, @code{-};
|
||||
@code{logand}, @code{logior}, @code{logxor}, @code{lognot} and their
|
||||
combinations; and @code{ash} with the positive second
|
||||
argument. ``Good'' widths are 32 on 32-bit CPUs and 64 on 64-bit CPUs.
|
||||
While it is possible to support smaller widths as well,
|
||||
As of SBCL 0.8.5 good functions are @code{+}, @code{-}, @code{logand}, @code{logior},
|
||||
@code{logxor}, @code{lognot} and their combinations; and @code{ash} with the positive
|
||||
second argument. Good widths are 32 on 32-bit CPUs and 64 on 64-bit
|
||||
CPUs. While it is possible to support smaller widths as well,
|
||||
currently this is not implemented.
|
||||
|
||||
@subsection Signed modular arithmetic
|
||||
@node signed modular arithmetic
|
||||
@subsection Signed Modular Arithmetic
|
||||
|
||||
Sign-extending the result in the following way will be translated into
|
||||
signed modular arithmetic:
|
||||
Sign-extending the result in the following way will be
|
||||
translated into signed modular arithmetic:
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(defun add (a b)
|
||||
(declare (type (signed-byte 64) a b))
|
||||
(let ((u (ldb (byte 64 0) (+ a b))))
|
||||
(logior u (- (mask-field (byte 1 63) u)))))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
@node recognized idioms
|
||||
@section Recognized Idioms
|
||||
|
||||
@node Recognized idioms
|
||||
@comment node-name, next, previous, up
|
||||
@section Recognized idioms
|
||||
@cindex Arithmetic, modular
|
||||
@cindex Arithmetic, hardware
|
||||
@menu
|
||||
* Count Trailing Zeros: count trailing zeros.
|
||||
@end menu
|
||||
|
||||
Common Lisp doesn't directly expose all features present in modern
|
||||
hardware. Some code patterns are recognized and turned into more
|
||||
efficient hardware instructions without requiring the use of internal
|
||||
features.
|
||||
Common Lisp doesn't directly expose all features present in
|
||||
modern hardware. Some code patterns are recognized and turned into
|
||||
more efficient hardware instructions without requiring the use of
|
||||
internal features.
|
||||
|
||||
@subsection Count trailing zeros
|
||||
@node count trailing zeros
|
||||
@subsection Count Trailing Zeros
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(defun ctz (n)
|
||||
(declare (type (unsigned-byte 64) n))
|
||||
(integer-length (ldb (byte 64 0) (lognor n (- n)))))
|
||||
@end lisp
|
||||
is turned into hardware instructions on arm64 and x86-64. It returns 64 when @code{n} is 0.
|
||||
@code{n} can also be @code{(signed-byte 64)} or @code{fixnum}.
|
||||
@end example
|
||||
|
||||
@node Global and Always-Bound variables
|
||||
@comment node-name, next, previous, up
|
||||
@section Global and Always-Bound variables
|
||||
is turned into hardware instructions on arm64 and x86-64. It returns
|
||||
64 when @code{n} is 0. @code{n} can also be @code{(signed-byte 64)} or @code{fixnum}.
|
||||
|
||||
@include macro-sb-ext-defglobal.texinfo
|
||||
@node global and always bound variables
|
||||
@section Global and Always-bound Variables
|
||||
|
||||
@deffn {Declaration} @sbext{global}
|
||||
@anchor{Macro sb-ext defglobal}
|
||||
@ffindex @sortas{defglobal sb-ext} defglobal [sb-ext]
|
||||
@deffn{Macro} sb-ext:defglobal name value &optional doc
|
||||
Defines @code{name} as a global variable that is always bound. @code{value} is evaluated
|
||||
and assigned to @code{name} both at compile- and load-time, but only if @code{name} is not
|
||||
already bound.
|
||||
|
||||
Syntax: @code{(sb-ext:global symbol*)}
|
||||
Global variables share their values between all threads, and cannot be
|
||||
locally bound, declared special, defined as constants, and neither bound
|
||||
nor defined as symbol macros.
|
||||
|
||||
See also the declarations @code{sb-ext:global} and @code{sb-ext:always-bound}.
|
||||
@end deffn
|
||||
@itemize
|
||||
@item [@strong{declaration}] @code{sb-ext:global}
|
||||
|
||||
Syntax: @code{(sb-ext:global &rest symbols)}
|
||||
|
||||
Only valid as a global proclamation.
|
||||
|
||||
Specifies that the named symbols cannot be proclaimed or locally
|
||||
declared @code{special}. Proclaiming an already special or constant
|
||||
variable name as @code{global} signal an error. Allows more efficient
|
||||
value lookup in threaded environments in addition to expressing
|
||||
programmer intention.
|
||||
@end deffn
|
||||
variable name as @code{sb-ext:global} signal an error. Allows more
|
||||
efficient value lookup in threaded environments in addition to
|
||||
expressing programmer intention.
|
||||
|
||||
@deffn {Declaration} @sbext{always-bound}
|
||||
@item [@strong{declaration}] @code{sb-ext:always-bound}
|
||||
|
||||
Syntax: @code{(sb-ext:always-bound symbol*)}
|
||||
Syntax: @code{(sb-ext:always-bound &rest symbols)}
|
||||
|
||||
Only valid as a global proclamation.
|
||||
|
||||
Specifies that the named symbols are always bound. Inhibits
|
||||
@code{makunbound} of the named symbols. Proclaiming an unbound symbol
|
||||
as @code{always-bound} signals an error. Allows the compiler to elide
|
||||
boundness checks from value lookups.
|
||||
@end deffn
|
||||
as @code{sb-ext:always-bound} signals an error. Allows the compiler to
|
||||
elide boundness checks from value lookups.
|
||||
@end itemize
|
||||
|
||||
@node Miscellaneous Efficiency Issues
|
||||
@comment node-name, next, previous, up
|
||||
@node miscellaneous efficiency issues
|
||||
@section Miscellaneous Efficiency Issues
|
||||
|
||||
FIXME: The material in the CMUCL manual about getting good
|
||||
|
|
@ -413,84 +417,60 @@ Besides this information from the CMUCL manual, there are a few other
|
|||
points to keep in mind.
|
||||
|
||||
@itemize
|
||||
|
||||
@item
|
||||
@findex @cl{let}
|
||||
@findex @cl{let*}
|
||||
@findex @cl{setq}
|
||||
@findex @cl{setf}
|
||||
The CMUCL manual doesn't seem to state it explicitly, but Python has a
|
||||
mental block about type inference when assignment is involved. Python
|
||||
is very aggressive and clever about inferring the types of values
|
||||
bound with @code{let}, @code{let*}, inline function call, and so
|
||||
forth. However, it's much more passive and dumb about inferring the
|
||||
types of values assigned with @code{setq}, @code{setf}, and
|
||||
friends. It would be nice to fix this, but in the meantime don't
|
||||
expect that just because it's very smart about types in most respects
|
||||
it will be smart about types involved in assignments. (This doesn't
|
||||
affect its ability to benefit from explicit type declarations
|
||||
involving the assigned variables, only its ability to get by without
|
||||
explicit type declarations.)
|
||||
|
||||
@c <!-- FIXME: Python dislikes assignments, but not in type
|
||||
@c inference. The real problems are loop induction, closed over
|
||||
@c variables and aliases. -->
|
||||
|
||||
@item
|
||||
Since the time the CMUCL manual was written, CMUCL (and thus SBCL) has
|
||||
gotten a generational garbage collector. This means that there are
|
||||
some efficiency implications of various patterns of memory usage which
|
||||
aren't discussed in the CMUCL manual. (Some new material should be
|
||||
written about this.)
|
||||
|
||||
@item
|
||||
SBCL has some important known efficiency problems. Perhaps the most
|
||||
important are
|
||||
|
||||
@itemize @minus
|
||||
|
||||
@item
|
||||
The garbage collector is not particularly efficient, at least on
|
||||
platforms without the generational collector (as of SBCL 0.8.9, all
|
||||
except x86).
|
||||
|
||||
@item
|
||||
Various aspects of the PCL implementation of CLOS are more inefficient
|
||||
than necessary.
|
||||
|
||||
@item The CMUCL manual doesn't seem to state it explicitly, but Python
|
||||
has a mental block about type inference when assignment is
|
||||
involved. Python is very aggressive and clever about inferring the
|
||||
types of values bound with @code{let}, @code{let*}, inline function call, and so
|
||||
forth. However, it's much more passive and dumb about inferring
|
||||
the types of values assigned with @code{setq}, @code{setf}, and friends. It
|
||||
would be nice to fix this, but in the meantime don't expect that
|
||||
just because it's very smart about types in most respects it will
|
||||
be smart about types involved in assignments. (This doesn't affect
|
||||
its ability to benefit from explicit type declarations involving
|
||||
the assigned variables, only its ability to get by without
|
||||
explicit type declarations.)
|
||||
@end itemize
|
||||
|
||||
@itemize
|
||||
@item Since the time the CMUCL manual was written, CMUCL (and thus SBCL)
|
||||
has gotten a generational garbage collector. This means that there
|
||||
are some efficiency implications of various patterns of memory
|
||||
usage which aren't discussed in the CMUCL manual. (Some new
|
||||
material should be written about this.)
|
||||
|
||||
@item SBCL has some important known efficiency problems. Perhaps the
|
||||
most important are
|
||||
|
||||
@itemize
|
||||
@item The garbage collector is not particularly efficient, at least
|
||||
on platforms without the generational collector (as of SBCL
|
||||
0.8.9, all except x86).
|
||||
|
||||
@item Various aspects of the PCL implementation of CLOS are more
|
||||
inefficient than necessary.
|
||||
@end itemize
|
||||
@end itemize
|
||||
|
||||
Finally, note that Common Lisp defines many constructs which, in
|
||||
the infamous phrase, ``could be compiled efficiently by a
|
||||
sufficiently smart compiler''. The phrase is infamous because
|
||||
making a compiler which actually is sufficiently smart to find all
|
||||
these optimizations systematically is well beyond the state of the art
|
||||
of current compiler technology. Instead, they're optimized on a
|
||||
case-by-case basis by hand-written code, or not optimized at all if
|
||||
the appropriate case hasn't been hand-coded. Some cases where no such
|
||||
Finally, note that Common Lisp defines many constructs which, in the
|
||||
infamous phrase, "could be compiled efficiently by a sufficiently
|
||||
smart compiler". The phrase is infamous because making a compiler
|
||||
which actually is sufficiently smart to find all these optimizations
|
||||
systematically is well beyond the state of the art of current
|
||||
compiler technology. Instead, they're optimized on a case-by-case
|
||||
basis by hand-written code, or not optimized at all if the
|
||||
appropriate case hasn't been hand-coded. Some cases where no such
|
||||
hand-coding has been done as of SBCL version 0.6.3 include
|
||||
|
||||
@itemize
|
||||
@item @code{(reduce #'f x)} where the type of @code{x} is known at compile time,
|
||||
|
||||
@item
|
||||
@code{(reduce #'f x)} where the type of @code{x} is known at compile
|
||||
time
|
||||
@item various bit vector operations, e.g. @code{(position 0 some-bit-vector)},
|
||||
|
||||
@item
|
||||
various bit vector operations, e.g. @code{(position 0
|
||||
some-bit-vector)}
|
||||
|
||||
@item
|
||||
specialized sequence idioms, e.g. @code{(remove item list :count 1)}
|
||||
|
||||
@item
|
||||
cases where local compilation policy does not require excessive type
|
||||
checking, e.g. @code{(locally (declare (safety 1)) (assoc item
|
||||
list))} (which currently performs safe @code{endp} checking internal
|
||||
to assoc).
|
||||
@item specialized sequence idioms, e.g. @code{(remove item list :count 1)},
|
||||
|
||||
@item cases where local compilation policy does not require excessive
|
||||
type checking, e.g. @code{(locally (declare (safety 1)) (assoc item list))}
|
||||
(which currently performs safe @code{endp} checking internal to @code{assoc}).
|
||||
@end itemize
|
||||
|
||||
If your system's performance is suffering because of some construct
|
||||
|
|
@ -498,5 +478,6 @@ which could in principle be compiled efficiently, but which the SBCL
|
|||
compiler can't in practice compile efficiently, consider writing a
|
||||
patch to the compiler and submitting it for inclusion in the main
|
||||
sources. Such code is often reasonably straightforward to write;
|
||||
search the sources for the string ``@code{deftransform}'' to find many
|
||||
search the sources for the string @code{deftransform} to find many
|
||||
examples (some straightforward, some less so).
|
||||
|
||||
|
|
|
|||
|
|
@ -1,173 +1,239 @@
|
|||
@node External Formats
|
||||
@comment node-name, next, previous, up
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node external formats
|
||||
@chapter External Formats
|
||||
|
||||
External formats determine the coding of characters from/to sequences of
|
||||
octets when exchanging data with the outside world. Examples of such
|
||||
exchanges are:
|
||||
|
||||
@enumerate
|
||||
|
||||
@item
|
||||
Character streams associated with files, sockets and process
|
||||
input/output (See @ref{Stream External Formats} and @ref{Running
|
||||
external programs})
|
||||
|
||||
@item
|
||||
Names of files
|
||||
|
||||
@item
|
||||
Foreign strings (See @ref{Foreign Types and Lisp Types})
|
||||
|
||||
@item
|
||||
Posix interface (See @ref{sb-posix})
|
||||
|
||||
@item
|
||||
Hostname- and protocol-related functions of the BSD-socket interface
|
||||
(See @ref{Networking})
|
||||
|
||||
@end enumerate
|
||||
|
||||
Technically, external formats in SBCL are named objects describing
|
||||
coding of characters as well as policies in case de- or encoding is not
|
||||
possible. Each external format has a canonical name and zero or more
|
||||
aliases. User code mostly interacts with external formats by supplying
|
||||
external format designators to functions that use external formats
|
||||
internally.
|
||||
|
||||
@menu
|
||||
* The Default External Format::
|
||||
* External Format Designators::
|
||||
* Character Coding Conditions::
|
||||
* Converting between Strings and Octet Vectors::
|
||||
* Supported External Formats::
|
||||
* The Default External Format: default external format.
|
||||
* External Format Designators: external format designators.
|
||||
* Character Coding Conditions: character coding conditions.
|
||||
* Converting between Strings and Octet Vectors: converting between strings and octet vectors.
|
||||
* Supported External Formats: supported external formats.
|
||||
@end menu
|
||||
|
||||
@node The Default External Format
|
||||
External formats determine the coding of characters from/to sequences
|
||||
of octets when exchanging data with the outside world. Examples of
|
||||
such exchanges are:
|
||||
|
||||
@itemize
|
||||
@item Character streams associated with files, sockets and process
|
||||
input/output (see @ref{stream external formats} and
|
||||
@ref{running external programs})
|
||||
|
||||
@item Names of files
|
||||
|
||||
@item Foreign strings (see @ref{foreign types and lisp types})
|
||||
|
||||
@item Posix interface (see @ref{sb posix})
|
||||
|
||||
@item Hostname- and protocol-related functions of the BSD-socket interface
|
||||
(see @ref{networking})
|
||||
@end itemize
|
||||
|
||||
Technically, external formats in SBCL are named objects describing
|
||||
coding of characters as well as policies in case de- or encoding is
|
||||
not possible. Each external format has a canonical name and zero or
|
||||
more aliases. User code mostly interacts with external formats by
|
||||
supplying external format designators to functions that use external
|
||||
formats internally.
|
||||
|
||||
@node default external format
|
||||
@section The Default External Format
|
||||
@cindex The Default External Format
|
||||
|
||||
Most functions interacting with external formats use a default external
|
||||
format if none is explicitly specified. In some cases, the default
|
||||
external format is used unconditionally.
|
||||
|
||||
The default external format is UTF-8. It can be changed via
|
||||
|
||||
@var{sb-ext:*default-external-format*}
|
||||
and
|
||||
@var{sb-ext:*default-c-string-external-format*}
|
||||
|
||||
@node External Format Designators
|
||||
@anchor{Variable sb-ext *default-external-format*}
|
||||
@vvindex @sortas{default-external-format* sb-ext} *default-external-format* [sb-ext]
|
||||
@deffn{Variable} sb-ext:*default-external-format*
|
||||
Most functions interacting with external formats (@code{open}, notably)
|
||||
use this default.
|
||||
@end deffn
|
||||
@anchor{Variable sb-ext *default-source-external-format*}
|
||||
@vvindex @sortas{default-source-external-format* sb-ext} *default-source-external-format* [sb-ext]
|
||||
@deffn{Variable} sb-ext:*default-source-external-format*
|
||||
@end deffn
|
||||
@anchor{Variable sb-ext *default-c-string-external-format*}
|
||||
@vvindex @sortas{default-c-string-external-format* sb-ext} *default-c-string-external-format* [sb-ext]
|
||||
@deffn{Variable} sb-ext:*default-c-string-external-format*
|
||||
@end deffn
|
||||
@node external format designators
|
||||
@section External Format Designators
|
||||
@cindex External Format Designators
|
||||
|
||||
@findex @cl{open}
|
||||
@findex @cl{with-open-file}
|
||||
In situations where an external format designator is required, such as
|
||||
the @code{:external-format} argument in calls to @code{open} or
|
||||
@code{with-open-file}, users may supply the name of an encoding to
|
||||
denote the external format which is applying that encoding to Lisp
|
||||
characters.
|
||||
the @code{:external-format} argument in calls to @code{open} or @code{with-open-file},
|
||||
users may supply the name of an encoding to denote the external
|
||||
format which is applying that encoding to Lisp characters.
|
||||
|
||||
In addition to the basic encoding for an external format, options
|
||||
controlling various special cases may be passed, by using a list (whose
|
||||
first element must be an encoding name and whose rest is a plist) as an
|
||||
external file format designator.
|
||||
controlling various special cases may be passed, by using a list
|
||||
(whose first element must be an encoding name and whose rest is a
|
||||
plist) as an external file format designator.
|
||||
|
||||
More specifically, external format designators can take the following
|
||||
forms:
|
||||
More specifically, external format designators can take the
|
||||
following forms:
|
||||
|
||||
@table @code
|
||||
@itemize
|
||||
@item @code{:default}: Designates the current default external format (see
|
||||
@ref{default external format}).
|
||||
|
||||
@item :default
|
||||
Designates the current default external format (See @ref{The Default
|
||||
External Format}).
|
||||
@item @code{<keyword>}: Designates the supported external format that has
|
||||
@code{<keyword>} as one of its names (see @ref{supported external formats}).
|
||||
|
||||
@item @var{keyword}
|
||||
Designates the supported external format that has @var{keyword} as one
|
||||
of its names. (See @ref{Supported External Formats}).
|
||||
@item @code{(<keyword> . <options-plist>)}: Designates an external format
|
||||
that is like the one designated by @code{<keyword>} with options as
|
||||
specified in @code{<options-plist>}.
|
||||
@end itemize
|
||||
|
||||
@item (@var{keyword} . @var{options-plist})
|
||||
Designates an external format that is like the one designated by
|
||||
@var{keyword} with options as specified in @var{options-plist}.
|
||||
Valid options for @code{<options-plist>} are:
|
||||
|
||||
@end table
|
||||
|
||||
Valid options for @var{options-plist} are:
|
||||
|
||||
@table @code
|
||||
|
||||
@item :newline @var{newline}
|
||||
@itemize
|
||||
@item @code{:NEWLINE <newline>}
|
||||
|
||||
An external format with an explicit @code{:newline} option is like its
|
||||
@var{keyword} parent, but recognizes certain characters or character
|
||||
sequences as newlines. For @code{:lf} (the default), the
|
||||
@code{<keyword>} parent but recognizes certain characters or
|
||||
character sequences as newlines. For @code{:lf} (the default), the
|
||||
@code{#\Linefeed} character is treated as @code{#\Newline} for both
|
||||
input and output. For @code{:cr}, @code{#\Return} is treated as
|
||||
@code{#\Newline}, while for @code{:crlf} the two-character sequence
|
||||
@code{#\Return #\Linefeed} is translated to and from @code{#\Newline}.
|
||||
@code{#\Return #\Linefeed} is translated to and from
|
||||
@code{#\Newline}.
|
||||
|
||||
@item :replacement @var{replacement}
|
||||
@item @code{:REPLACEMENT <replacement>}
|
||||
|
||||
An external format with an explicit @code{:replacement} option is like
|
||||
its @var{keyword} parent, but does not signal an error in case a
|
||||
character or octet sequence cannot be en- or decoded. Instead, it
|
||||
inserts @var{replacement} at the position in
|
||||
question. @var{replacement} has to be a string designator, that is a
|
||||
character or string.
|
||||
its @code{<keyword>} parent but does not signal an error in case a
|
||||
character or octet sequence cannot be en- or decoded. Instead,
|
||||
it inserts @code{<replacement>} at the position in question.
|
||||
@code{<replacement>} must be a string designator; that is, a
|
||||
character or a string.
|
||||
@end itemize
|
||||
|
||||
For example:
|
||||
@lisp
|
||||
|
||||
@example
|
||||
(with-open-file (stream pathname :external-format '(:utf-8 :replacement #\?))
|
||||
(read-line stream))
|
||||
@end lisp
|
||||
will read the first line of @var{pathname}, replacing any octet sequence
|
||||
that is not valid in the UTF-8 external format with a question mark
|
||||
character.
|
||||
@end example
|
||||
|
||||
@end table
|
||||
will read the first line of @code{pathname}, replacing any octet
|
||||
sequence that is not valid in the UTF-8 external format with a
|
||||
question mark character.
|
||||
|
||||
@node Character Coding Conditions
|
||||
@node character coding conditions
|
||||
@section Character Coding Conditions
|
||||
@cindex Character Coding Conditions
|
||||
|
||||
De- or encoding characters using a given external format is not always
|
||||
possible:
|
||||
|
||||
@itemize
|
||||
@item Decoding an octet vector using a given external format can fail if
|
||||
it contains an octet or sequence of octets that does not have an
|
||||
interpretation as a character according to the external format.
|
||||
|
||||
@item
|
||||
Decoding an octet vector using a given external format can fail if it
|
||||
contains an octet or sequence of octets that does not have an
|
||||
interpretation as a character according to the external format.
|
||||
|
||||
@item
|
||||
Conversely, a string may contain characters that a given external format
|
||||
cannot encode. For example, the ASCII external format cannot encode the
|
||||
character @code{#\ö}.
|
||||
|
||||
@item Conversely, a string may contain characters that a given external
|
||||
format cannot encode. For example, the ASCII external format
|
||||
cannot encode the character @code{#\ö}.
|
||||
@end itemize
|
||||
|
||||
Unless the external format governing the coding uses the
|
||||
@code{:replacement} keyword, SBCL will signal (continuable) errors under
|
||||
the above circumstances. The types of the condition signaled are not
|
||||
currently exported or documented but will be in future SBCL versions.
|
||||
@code{:replacement} option, SBCL will signal (continuable) errors under the
|
||||
above circumstances. The types of the condition signaled are not
|
||||
currently exported or documented but will be in future SBCL
|
||||
versions.
|
||||
|
||||
@node Converting between Strings and Octet Vectors
|
||||
@node converting between strings and octet vectors
|
||||
@section Converting between Strings and Octet Vectors
|
||||
@cindex Converting between Strings and Octet Vectors
|
||||
|
||||
To encode Lisp strings as octet vectors and decode octet vectors as Lisp
|
||||
strings, the following SBCL-specific functions can be used:
|
||||
To encode Lisp strings as octet vectors and decode octet vectors as
|
||||
Lisp strings, the following SBCL-specific functions can be used:
|
||||
|
||||
@include fun-sb-ext-string-to-octets.texinfo
|
||||
@include fun-sb-ext-octets-to-string.texinfo
|
||||
@anchor{Function sb-ext string-to-octets}
|
||||
@ffindex @sortas{string-to-octets sb-ext} string-to-octets [sb-ext]
|
||||
@deffn{Function} sb-ext:string-to-octets string &key external-format start end null-terminate
|
||||
Return an octet vector that is @code{string} encoded according to @code{external-format}.
|
||||
|
||||
@node Supported External Formats
|
||||
If @code{external-format} is given, it must designate an external format.
|
||||
|
||||
If given, @code{start} and @code{end} must be bounding index designators and
|
||||
designate a subsequence of @code{string} that should be encoded.
|
||||
|
||||
If @code{null-terminate} is true, the returned octet vector ends with an
|
||||
additional 0 element that does not correspond to any part of @code{string}.
|
||||
|
||||
If some of the characters of @code{string} (or the subsequence bounded by
|
||||
@code{start} and @code{end}) cannot be encoded by @code{external-format} an error of a
|
||||
subtype of @code{sb-int:character-encoding-error} is signaled.
|
||||
|
||||
Note that for some values of @code{external-format} and @code{null-terminate} the
|
||||
length of the returned vector may be different from the length of
|
||||
@code{string} (or the subsequence bounded by @code{start} and @code{end}).
|
||||
@end deffn
|
||||
@anchor{Function sb-ext octets-to-string}
|
||||
@ffindex @sortas{octets-to-string sb-ext} octets-to-string [sb-ext]
|
||||
@deffn{Function} sb-ext:octets-to-string vector &key external-format start end
|
||||
Return a string obtained by decoding @code{vector} according to @code{external-format}.
|
||||
|
||||
If @code{external-format} is given, it must designate an external format.
|
||||
|
||||
If given, @code{start} and @code{end} must be bounding index designators and
|
||||
designate a subsequence of @code{vector} that should be decoded.
|
||||
|
||||
If some of the octets of @code{vector} (or the subsequence bounded by @code{start}
|
||||
and @code{end}) cannot be decoded by @code{external-format} an error of a subtype of
|
||||
@code{sb-int:character-decoding-error} is signaled.
|
||||
|
||||
Note that for some values of @code{external-format} the length of the
|
||||
returned string may be different from the length of @code{vector} (or the
|
||||
subsequence bounded by @code{start} and @code{end}).
|
||||
@end deffn
|
||||
@node supported external formats
|
||||
@section Supported External Formats
|
||||
@cindex Supported External Formats
|
||||
|
||||
The following table lists the external formats supported by SBCL in the
|
||||
form of the respective canonical name followed by the list of aliases:
|
||||
The following lists the external formats supported by SBCL in
|
||||
the form of the respective canonical name followed by the list of aliases:
|
||||
|
||||
@itemize
|
||||
@item @code{:euc-jp}
|
||||
|
||||
@code{:eucjp}, @code{:|eucJP|}
|
||||
|
||||
@item @code{:gbk}
|
||||
|
||||
@code{:cp936}
|
||||
|
||||
@item @code{:shift_jis}
|
||||
|
||||
@code{:sjis}, @code{:|Shift_JIS|}, @code{:cp932}
|
||||
|
||||
@item @code{:ucs-2be}
|
||||
|
||||
@code{:ucs2be}
|
||||
|
||||
@item @code{:ucs-2le}
|
||||
|
||||
@code{:ucs2le}
|
||||
|
||||
@item @code{:ucs-4be}
|
||||
|
||||
@code{:ucs4be}
|
||||
|
||||
@item @code{:ucs-4le}
|
||||
|
||||
@code{:ucs4le}
|
||||
|
||||
@item @code{:utf-16be}
|
||||
|
||||
@code{:utf16be}
|
||||
|
||||
@item @code{:utf-16le}
|
||||
|
||||
@code{:utf16le}
|
||||
|
||||
@item @code{:utf-32be}
|
||||
|
||||
@code{:utf32be}
|
||||
|
||||
@item @code{:utf-32le}
|
||||
|
||||
@code{:utf32le}
|
||||
@end itemize
|
||||
|
||||
|
||||
@include encodings.texi-temp
|
||||
|
|
|
|||
File diff suppressed because it is too large
Load diff
|
|
@ -1,223 +0,0 @@
|
|||
@node Gray Streams examples
|
||||
@subsection Gray Streams examples
|
||||
|
||||
@macro codew{stuff}
|
||||
@code{@w{\stuff\}}
|
||||
@end macro
|
||||
|
||||
Below are two classes of stream that can be conveniently defined as
|
||||
wrappers for Common Lisp streams. These are meant to serve as
|
||||
examples of minimal implementations of the protocols that must be
|
||||
followed when defining Gray streams. Realistic uses of the Gray
|
||||
Streams API would implement the various methods that can do I/O in
|
||||
batches, such as @codew{stream-read-line}, @codew{stream-write-string},
|
||||
@codew{stream-read-sequence}, and @codew{stream-write-sequence}.
|
||||
|
||||
|
||||
@menu
|
||||
* Character counting input stream::
|
||||
* Output prefixing character stream::
|
||||
@end menu
|
||||
|
||||
@node Character counting input stream
|
||||
@subsubsection Character counting input stream
|
||||
|
||||
It is occasionally handy for programs that process input files to
|
||||
count the number of characters and lines seen so far, and the number
|
||||
of characters seen on the current line, so that useful messages may be
|
||||
reported in case of parsing errors, etc. Here is a character input
|
||||
stream class that keeps track of these counts. Note that all
|
||||
character input streams must implement @codew{stream-read-char} and
|
||||
@codew{stream-unread-char}.
|
||||
|
||||
@lisp
|
||||
@group
|
||||
(defclass wrapped-stream (fundamental-stream)
|
||||
((stream :initarg :stream :reader stream-of)))
|
||||
@end group
|
||||
@group
|
||||
(defmethod stream-element-type ((stream wrapped-stream))
|
||||
(stream-element-type (stream-of stream)))
|
||||
@end group
|
||||
@group
|
||||
(defmethod close ((stream wrapped-stream) &key abort)
|
||||
(close (stream-of stream) :abort abort))
|
||||
@end group
|
||||
@group
|
||||
(defclass wrapped-character-input-stream
|
||||
(wrapped-stream fundamental-character-input-stream)
|
||||
())
|
||||
@end group
|
||||
@group
|
||||
(defmethod stream-read-char ((stream wrapped-character-input-stream))
|
||||
(read-char (stream-of stream) nil :eof))
|
||||
@end group
|
||||
@group
|
||||
(defmethod stream-unread-char ((stream wrapped-character-input-stream)
|
||||
char)
|
||||
(unread-char char (stream-of stream)))
|
||||
@end group
|
||||
@group
|
||||
(defclass counting-character-input-stream
|
||||
(wrapped-character-input-stream)
|
||||
((char-count :initform 1 :accessor char-count-of)
|
||||
(line-count :initform 1 :accessor line-count-of)
|
||||
(col-count :initform 1 :accessor col-count-of)
|
||||
(prev-col-count :initform 1 :accessor prev-col-count-of)))
|
||||
@end group
|
||||
@group
|
||||
(defmethod stream-read-char ((stream counting-character-input-stream))
|
||||
(with-accessors ((inner-stream stream-of) (chars char-count-of)
|
||||
(lines line-count-of) (cols col-count-of)
|
||||
(prev prev-col-count-of)) stream
|
||||
(let ((char (call-next-method)))
|
||||
(cond ((eql char :eof)
|
||||
:eof)
|
||||
((char= char #\Newline)
|
||||
(incf lines)
|
||||
(incf chars)
|
||||
(setf prev cols)
|
||||
(setf cols 1)
|
||||
char)
|
||||
(t
|
||||
(incf chars)
|
||||
(incf cols)
|
||||
char)))))
|
||||
@end group
|
||||
@group
|
||||
(defmethod stream-unread-char ((stream counting-character-input-stream)
|
||||
char)
|
||||
(with-accessors ((inner-stream stream-of) (chars char-count-of)
|
||||
(lines line-count-of) (cols col-count-of)
|
||||
(prev prev-col-count-of)) stream
|
||||
(cond ((char= char #\Newline)
|
||||
(decf lines)
|
||||
(decf chars)
|
||||
(setf cols prev))
|
||||
(t
|
||||
(decf chars)
|
||||
(decf cols)
|
||||
char))
|
||||
(call-next-method)))
|
||||
@end group
|
||||
@end lisp
|
||||
|
||||
The default methods for @codew{stream-read-char-no-hang},
|
||||
@codew{stream-peek-char}, @codew{stream-listen},
|
||||
@codew{stream-clear-input}, @codew{stream-read-line}, and
|
||||
@codew{stream-read-sequence} should be sufficient (though the last two
|
||||
will probably be slower than methods that forwarded directly).
|
||||
|
||||
Here's a sample use of this class:
|
||||
|
||||
@lisp
|
||||
@group
|
||||
(with-input-from-string (input "1 2
|
||||
3 :foo ")
|
||||
(let ((counted-stream (make-instance 'counting-character-input-stream
|
||||
:stream input)))
|
||||
(loop for thing = (read counted-stream) while thing
|
||||
unless (numberp thing) do
|
||||
(error "Non-number ~S (line ~D, column ~D)" thing
|
||||
(line-count-of counted-stream)
|
||||
(- (col-count-of counted-stream)
|
||||
(length (format nil "~S" thing))))
|
||||
end
|
||||
do (print thing))))
|
||||
@end group
|
||||
@verbatim
|
||||
1
|
||||
2
|
||||
3
|
||||
Non-number :FOO (line 2, column 5)
|
||||
[Condition of type SIMPLE-ERROR]
|
||||
@end verbatim
|
||||
@end lisp
|
||||
|
||||
@node Output prefixing character stream
|
||||
@subsubsection Output prefixing character stream
|
||||
|
||||
One use for a wrapped output stream might be to prefix each line of
|
||||
text with a timestamp, e.g., for a logging stream. Here's a simple
|
||||
stream that does this, though without any fancy line-wrapping. Note
|
||||
that all character output stream classes must implement
|
||||
@codew{stream-write-char} and @codew{stream-line-column}.
|
||||
|
||||
@lisp
|
||||
@group
|
||||
(defclass wrapped-stream (fundamental-stream)
|
||||
((stream :initarg :stream :reader stream-of)))
|
||||
@end group
|
||||
@group
|
||||
(defmethod stream-element-type ((stream wrapped-stream))
|
||||
(stream-element-type (stream-of stream)))
|
||||
@end group
|
||||
@group
|
||||
(defmethod close ((stream wrapped-stream) &key abort)
|
||||
(close (stream-of stream) :abort abort))
|
||||
@end group
|
||||
@group
|
||||
(defclass wrapped-character-output-stream
|
||||
(wrapped-stream fundamental-character-output-stream)
|
||||
((col-index :initform 0 :accessor col-index-of)))
|
||||
@end group
|
||||
@group
|
||||
(defmethod stream-line-column ((stream wrapped-character-output-stream))
|
||||
(col-index-of stream))
|
||||
@end group
|
||||
@group
|
||||
(defmethod stream-write-char ((stream wrapped-character-output-stream)
|
||||
char)
|
||||
(with-accessors ((inner-stream stream-of) (cols col-index-of)) stream
|
||||
(write-char char inner-stream)
|
||||
(if (char= char #\Newline)
|
||||
(setf cols 0)
|
||||
(incf cols))))
|
||||
@end group
|
||||
@group
|
||||
(defclass prefixed-character-output-stream
|
||||
(wrapped-character-output-stream)
|
||||
((prefix :initarg :prefix :reader prefix-of)))
|
||||
@end group
|
||||
@group
|
||||
(defgeneric write-prefix (prefix stream)
|
||||
(:method ((prefix string) stream) (write-string prefix stream))
|
||||
(:method ((prefix function) stream) (funcall prefix stream)))
|
||||
@end group
|
||||
@group
|
||||
(defmethod stream-write-char ((stream prefixed-character-output-stream)
|
||||
char)
|
||||
(with-accessors ((inner-stream stream-of) (cols col-index-of)
|
||||
(prefix prefix-of)) stream
|
||||
(when (zerop cols)
|
||||
(write-prefix prefix inner-stream))
|
||||
(call-next-method)))
|
||||
@end group
|
||||
@end lisp
|
||||
|
||||
As with the example input stream, this implements only the minimal
|
||||
protocol. A production implementation should also provide methods for
|
||||
at least @codew{stream-write-line}, @codew{stream-write-sequence}.
|
||||
|
||||
And here's a sample use of this class:
|
||||
|
||||
@lisp
|
||||
@group
|
||||
(flet ((format-timestamp (stream)
|
||||
(apply #'format stream "[~2@@*~2,' D:~1@@*~2,'0D:~0@@*~2,'0D] "
|
||||
(multiple-value-list (get-decoded-time)))))
|
||||
(let ((output (make-instance 'prefixed-character-output-stream
|
||||
:stream *standard-output*
|
||||
:prefix #'format-timestamp)))
|
||||
(loop for string in '("abc" "def" "ghi") do
|
||||
(write-line string output)
|
||||
(sleep 1))))
|
||||
@end group
|
||||
@verbatim
|
||||
[ 0:30:05] abc
|
||||
[ 0:30:06] def
|
||||
[ 0:30:07] ghi
|
||||
NIL
|
||||
@end verbatim
|
||||
@end lisp
|
||||
@unmacro codew
|
||||
|
|
@ -1,210 +1,172 @@
|
|||
@node Introduction
|
||||
@comment node-name, next, previous, up
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node introduction
|
||||
@chapter Introduction
|
||||
|
||||
@menu
|
||||
* ANSI Conformance: ansi conformance.
|
||||
* Extensions: extensions.
|
||||
* Idiosyncrasies: idiosyncrasies.
|
||||
* Development Tools: development tools.
|
||||
* More SBCL Information: more sbcl information.
|
||||
* More Common Lisp Information: more common lisp information.
|
||||
* History and Implementation of SBCL: history and implementation of sbcl.
|
||||
@end menu
|
||||
|
||||
SBCL is a mostly-conforming implementation of the ANSI Common Lisp
|
||||
standard. This manual focuses on behavior which is specific to SBCL,
|
||||
not on behavior which is common to all implementations of ANSI Common
|
||||
Lisp.
|
||||
|
||||
@menu
|
||||
* ANSI Conformance::
|
||||
* Extensions::
|
||||
* Idiosyncrasies::
|
||||
* Development Tools::
|
||||
* More SBCL Information::
|
||||
* More Common Lisp Information::
|
||||
* History and Implementation of SBCL::
|
||||
@end menu
|
||||
|
||||
|
||||
|
||||
@node ANSI Conformance
|
||||
@comment node-name, next, previous, up
|
||||
@node ansi conformance
|
||||
@section ANSI Conformance
|
||||
|
||||
Essentially every type of non-conformance is considered a bug. (The
|
||||
exceptions involve internal inconsistencies in the standard.)
|
||||
@xref{Reporting Bugs}.
|
||||
|
||||
@subsection Exceptions
|
||||
exceptions involve internal inconsistencies in the standard.) See
|
||||
@ref{reporting bugs}.
|
||||
|
||||
@itemize
|
||||
@item @code{prog2} returns the primary value of its second form, as
|
||||
specified in the @emph{Arguments and Values} section of the
|
||||
specification for that operator, not that of its first form, as
|
||||
specified in the @emph{Description}.
|
||||
|
||||
@item
|
||||
@findex @cl{prog2}
|
||||
@code{prog2} returns the primary value of its second form, as
|
||||
specified in the @strong{Arguments and Values} section of the
|
||||
specification for that operator, not that of its first form, as
|
||||
specified in the @strong{Description}.
|
||||
|
||||
@item
|
||||
@tindex @cl{string}
|
||||
@tindex @cl{character}
|
||||
@tindex @cl{nil}
|
||||
The @code{string} type is considered to be the union of all types
|
||||
@code{(array @emph{c} (@emph{size}))} for all non-@code{nil} subtypes @code{@emph{c}} of
|
||||
@code{character}, excluding arrays specialized to the empty type.
|
||||
|
||||
@item
|
||||
@findex @cl{define-method-combination}
|
||||
@vindex @cl{nil}
|
||||
The @code{:order} long form option in @code{define-method-combination}
|
||||
method group specifiers accepts the value @code{nil} as well as
|
||||
@code{:most-specific-first} and @code{:most-specific-last}, in order
|
||||
to allow programmers to declare that the order of methods playing that
|
||||
role in the method combination does not matter.
|
||||
@item The @code{string} type is considered to be the union of all types
|
||||
@code{(array c (size))} for all non-@code{nil} subtypes @code{c} of @code{character},
|
||||
excluding arrays specialized to the empty type.
|
||||
|
||||
@item The @code{:order} long form option in @code{define-method-combination} method
|
||||
group specifiers accepts the value @code{nil} as well as
|
||||
@code{:most-specific-first} and @code{:most-specific-last}, in order to allow
|
||||
programmers to declare that the order of methods playing that role
|
||||
in the method combination does not matter.
|
||||
@end itemize
|
||||
|
||||
@node Extensions
|
||||
@comment node-name, next, previous, up
|
||||
@node extensions
|
||||
@section Extensions
|
||||
|
||||
SBCL comes with numerous extensions, some in core and some in modules
|
||||
loadable with @code{require}. Unfortunately, not all of these
|
||||
extensions have proper documentation yet.
|
||||
loadable with @code{require}. Unfortunately, not all of these extensions
|
||||
have proper documentation yet.
|
||||
|
||||
@c FIXME: Once bits and pieces referred to here get real documentation
|
||||
@c add xrefs there.
|
||||
@itemize
|
||||
@item @strong{System Definition Tool:} ASDF is a flexible and popular
|
||||
protocol-oriented system definition tool by Daniel Barlow.
|
||||
|
||||
@table @strong
|
||||
@item @strong{Foreign Function Interface:} The @code{sb-alien} package allows
|
||||
interfacing with C-code, loading shared object files, etc. See
|
||||
@ref{foreign function interface}.
|
||||
|
||||
@item System Definition Tool
|
||||
@code{asdf} is a flexible and popular protocol-oriented system
|
||||
definition tool by Daniel Barlow. @xref{Top, , , asdf} for more
|
||||
information.
|
||||
@ref{sb grovel} can be used to partially automate generation of
|
||||
foreign function interface definitions.
|
||||
|
||||
@item Foreign Function Interface
|
||||
@code{sb-alien} package allows interfacing with C-code, loading shared
|
||||
object files, etc. @xref{Foreign Function Interface}.
|
||||
@item @strong{Recursive Event Loop:} SBCL provides a recursive event
|
||||
loop (@code{serve-event}) for doing non-blocking IO on multiple streams
|
||||
without using threads.
|
||||
|
||||
@code{sb-grovel} can be used to partially automate generation of
|
||||
foreign function interface definitions. @xref{sb-grovel}.
|
||||
@item @strong{Timeouts and Deadlines:} SBCL allows restricting the execution
|
||||
time of individual operations or parts of a computation using
|
||||
@code{:timeout} arguments to certain blocking operations, synchronous
|
||||
timeouts and asynchronous timeouts. The latter two affect operations
|
||||
without explicit timeout support (such as standard functions and
|
||||
macros). See @ref{timeouts and deadlines}.
|
||||
|
||||
@item Recursive Event Loop
|
||||
SBCL provides a recursive event loop (@code{serve-event}) for doing
|
||||
non-blocking IO on multiple streams without using threads.
|
||||
@item @strong{Metaobject Protocol:} The @code{sb-mop} package provides an
|
||||
implementation of the metaobject protocol for the Common Lisp
|
||||
Object System as described in @emph{The Art of the Metaobject Protocol}
|
||||
by Kiczales et al.
|
||||
|
||||
@item Timeouts and Deadlines
|
||||
SBCL allows restricting the execution time of individual operations or
|
||||
parts of a computation using @code{:timeout} arguments to certain
|
||||
blocking operations, synchronous timeouts and asynchronous timeouts. The
|
||||
latter two affect operations without explicit timeout support (such as
|
||||
standard functions and macros). @xref{Timeouts and Deadlines}.
|
||||
@item @strong{Extensible Sequences:} SBCL allows users to define subclasses
|
||||
of the @code{sequence} class. See @ref{extensible sequences}.
|
||||
|
||||
@item Metaobject Protocol
|
||||
@code{sb-mop} package provides a metaobject protocol for the Common
|
||||
Lisp Object System as described in @cite{Art of Metaobject Protocol}.
|
||||
@item @strong{Native Threads:} SBCL has native threads on numerous platforms,
|
||||
capable of taking advantage of SMP on multiprocessor machines. See
|
||||
@ref{threading}.
|
||||
|
||||
@item Extensible Sequences
|
||||
SBCL allows users to define subclasses of the @code{sequence}
|
||||
class. @xref{Extensible Sequences}.
|
||||
@item @strong{Network Interface:} The @code{sb-bsd-sockets} module is a low-level
|
||||
networking interface, providing both TCP and UDP sockets. See
|
||||
@ref{networking}.
|
||||
|
||||
@item Native Threads
|
||||
SBCL has native threads on x86/Linux, capable of taking advantage
|
||||
of SMP on multiprocessor machines. @xref{Threading}.
|
||||
@item @strong{Introspective Facilities:} The @ref{sb introspect} module offers
|
||||
numerous introspective extensions, including access to function
|
||||
lambda-lists and a cross referencing facility.
|
||||
|
||||
@item Network Interface
|
||||
@code{sb-bsd-sockets} is a low-level networking interface, providing
|
||||
both TCP and UDP sockets. @xref{Networking}.
|
||||
@item @strong{Operating System Interface:} The @code{sb-ext} package contains a
|
||||
number of functions for running external processes, accessing
|
||||
environment variables, etc.
|
||||
|
||||
@item Introspective Facilities
|
||||
@code{sb-introspect} module offers numerous introspective extensions,
|
||||
including access to function lambda-lists and a cross referencing
|
||||
facility.
|
||||
The @ref{sb posix} module provides a lispy interface to standard
|
||||
POSIX facilities.
|
||||
|
||||
@item Operating System Interface
|
||||
@code{sb-ext} contains a number of functions for running external
|
||||
processes, accessing environment variables, etc.
|
||||
@item @strong{Extensible Streams:} The package @code{sb-gray} provides an
|
||||
implementation of @ref{gray streams}.
|
||||
|
||||
@code{sb-posix} module provides a lispy interface to standard POSIX
|
||||
facilities.
|
||||
The @ref{sb simple streams} module is an implementation of the Simple
|
||||
Streams API proposed by Franz Inc.
|
||||
|
||||
@item Extensible Streams
|
||||
@code{sb-gray} is an implementation of @emph{Gray Streams}. @xref{Gray
|
||||
Streams}.
|
||||
@item @strong{Profiling:} The @code{sb-profile} package provides an exact,
|
||||
per-function @ref{deterministic profiler}.
|
||||
|
||||
@code{sb-simple-streams} is an implementation of the @emph{simple
|
||||
streams} API proposed by Franz Inc. @xref{Simple Streams}.
|
||||
The @code{sb-sprof} module is SBCL's @ref{statistical profiler}, capable
|
||||
of call-graph generation and instruction level profiling, which
|
||||
also supports allocation profiling.
|
||||
|
||||
@item Profiling
|
||||
@code{sb-profile} is a exact per-function profiler. @xref{Deterministic
|
||||
Profiler}.
|
||||
@item @strong{Customization Hooks:} SBCL contains a number of extra-standard
|
||||
customization hooks that can be used to tweak the behaviour of the
|
||||
system. See @ref{customization hooks for users}.
|
||||
|
||||
@code{sb-sprof} is a statistical profiler, capable of call-graph
|
||||
generation and instruction level profiling, which also supports
|
||||
allocation profiling. @xref{Statistical Profiler}.
|
||||
@item @strong{sb-aclrepl:} The @ref{sb aclrepl} module provides an Allegro-style
|
||||
toplevel for SBCL, as an alternative to the classic CMUCL-style
|
||||
one.
|
||||
|
||||
@item Customization Hooks
|
||||
SBCL contains a number of extra-standard customization hooks that
|
||||
can be used to tweak the behaviour of the system. @xref{Customization
|
||||
Hooks for Users}.
|
||||
@item @strong{CLTL2 Compatibility Layer:} The SB-CLTL2 module provides
|
||||
@code{sb-cltl2:compiler-let} and environment access functionality
|
||||
described in @emph{Common Lisp The Language, 2nd Edition} which were
|
||||
removed from the language during the ANSI standardization process.
|
||||
|
||||
@code{sb-aclrepl} provides an Allegro CL -style toplevel for SBCL,
|
||||
as an alternative to the classic CMUCL-style one. @xref{sb-aclrepl}.
|
||||
@item @strong{Executable Delivery:} The @code{:executable} argument to
|
||||
@code{sb-ext:save-lisp-and-die} can produce a "standalone" executable
|
||||
containing both an image of the current Lisp session and an SBCL
|
||||
runtime.
|
||||
|
||||
@item CLTL2 Compatibility Layer
|
||||
@code{sb-cltl2} module provides @code{compiler-let} and environment
|
||||
access functionality described in @cite{Common Lisp The Language, 2nd
|
||||
Edition} which were removed from the language during the ANSI
|
||||
standardization process.
|
||||
@item @strong{Bitwise Rotation:} The @ref{sb rotate byte} module provides an
|
||||
efficient primitive for bitwise rotation of integers, an operation
|
||||
required by e.g. numerous cryptographic algorithms but not
|
||||
available as a primitive in ANSI Common Lisp.
|
||||
|
||||
@item Executable Delivery
|
||||
The @code{:executable} argument to @ref{Function
|
||||
sb-ext save-lisp-and-die} can produce a `standalone' executable
|
||||
containing both an image of the current Lisp session and an SBCL
|
||||
runtime.
|
||||
@item @strong{Test Harness:} The @code{sb-rt} module is a simple yet attractive
|
||||
regression and unit-test framework.
|
||||
|
||||
@item Bitwise Rotation
|
||||
@code{sb-rotate-byte} provides an efficient primitive for bitwise
|
||||
rotation of integers, an operation required by e.g. numerous
|
||||
cryptographic algorithms, but not available as a primitive in ANSI
|
||||
Common Lisp. @xref{sb-rotate-byte}.
|
||||
@item @strong{MD5 Sums:} The @ref{sb md5} module provides an implementation of the
|
||||
MD5 message digest algorithm for Common Lisp, using the modular
|
||||
arithmetic optimizations provided by SBCL.
|
||||
@end itemize
|
||||
|
||||
@item Test Harness
|
||||
@code{sb-rt} module is a simple yet attractive regression and
|
||||
unit-test framework.
|
||||
|
||||
@item MD5 Sums
|
||||
@code{sb-md5} is an implementation of the MD5 message digest algorithm
|
||||
for Common Lisp, using the modular arithmetic optimizations provided
|
||||
by SBCL. @xref{sb-md5}.
|
||||
|
||||
@end table
|
||||
|
||||
|
||||
|
||||
|
||||
@node Idiosyncrasies
|
||||
@comment node-name, next, previous, up
|
||||
@node idiosyncrasies
|
||||
@section Idiosyncrasies
|
||||
|
||||
@menu
|
||||
* Declarations: declarations.
|
||||
* FASL format: fasl format.
|
||||
* Compiler-only Implementation: compiler only implementation.
|
||||
* Defining Constants: defining constants.
|
||||
* Style Warnings: style warnings.
|
||||
@end menu
|
||||
|
||||
The information in this section describes some of the ways that SBCL
|
||||
deals with choices that the ANSI standard leaves to the
|
||||
implementation.
|
||||
|
||||
@menu
|
||||
* Declarations::
|
||||
* FASL Format::
|
||||
* Compiler-only Implementation::
|
||||
* Defining Constants::
|
||||
* Style Warnings::
|
||||
@end menu
|
||||
|
||||
@node Declarations
|
||||
@comment node-name, next, previous, up
|
||||
@node declarations
|
||||
@subsection Declarations
|
||||
|
||||
Declarations are generally treated as assertions. This general
|
||||
principle, and its implications, and the bugs which still keep the
|
||||
compiler from quite satisfying this principle, are discussed in
|
||||
@ref{Declarations as Assertions}.
|
||||
@ref{declarations as assertions}.
|
||||
|
||||
|
||||
@node FASL Format
|
||||
@comment node-name, next, previous, up
|
||||
@subsection FASL Format
|
||||
@node fasl format
|
||||
@subsection FASL format
|
||||
|
||||
SBCL fasl-format is binary compatible only with the exact SBCL version
|
||||
it was generated with. While this is obviously suboptimal, it has
|
||||
|
|
@ -213,10 +175,10 @@ versions: accidentally breaking things is far too easy, and can lead
|
|||
to hard to diagnose bugs.
|
||||
|
||||
The following snippet handles fasl recompilation automatically for
|
||||
ASDF-based systems, and makes a good candidate for inclusion in
|
||||
the user or system initialization file (@pxref{Initialization Files}.)
|
||||
ASDF-based systems, and makes a good candidate for inclusion in the
|
||||
user or system initialization file (see @ref{initialization files}).
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(require :asdf)
|
||||
|
||||
;;; If a fasl was stale, try to recompile and load (once).
|
||||
|
|
@ -227,328 +189,302 @@ the user or system initialization file (@pxref{Initialization Files}.)
|
|||
(sb-ext:invalid-fasl ()
|
||||
(asdf:perform (make-instance 'asdf:compile-op) c)
|
||||
(call-next-method))))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
|
||||
@node Compiler-only Implementation
|
||||
@comment node-name, next, previous, up
|
||||
@node compiler only implementation
|
||||
@subsection Compiler-only Implementation
|
||||
|
||||
SBCL is essentially a compiler-only implementation of Common Lisp.
|
||||
That is, for all but a few special cases, @code{eval} creates a lambda
|
||||
expression, calls @code{compile} on the lambda expression to create a
|
||||
compiled function, and then calls @code{funcall} on the resulting
|
||||
function object. A more traditional interpreter is also available on
|
||||
default builds; it is usually only called internally. This is
|
||||
explicitly allowed by the ANSI standard, but leads to some oddities;
|
||||
e.g. at default settings, @code{functionp} and
|
||||
@code{compiled-function-p} are equivalent, and they collapse into the
|
||||
same function when SBCL is built without the interpreter.
|
||||
compiled function, and then calls @code{funcall} on the resulting function
|
||||
object. A more traditional interpreter is also available on default
|
||||
builds; it is usually only called internally. This is explicitly
|
||||
allowed by the ANSI standard but leads to some oddities; e.g. at
|
||||
default settings, @code{functionp} and @code{compiled-function-p} are equivalent,
|
||||
and they collapse into the same function when SBCL is built without
|
||||
the interpreter.
|
||||
|
||||
@node Defining Constants
|
||||
@comment node-name, next, previous, up
|
||||
@node defining constants
|
||||
@subsection Defining Constants
|
||||
@findex @cl{defconstant}
|
||||
|
||||
SBCL is quite strict about ANSI's definition of @code{defconstant}.
|
||||
ANSI says that doing @code{defconstant} of the same symbol more than
|
||||
once is undefined unless the new value is @code{eql} to the old value.
|
||||
Conforming to this specification is a nuisance when the ``constant''
|
||||
value is only constant under some weaker test like @code{string=} or
|
||||
@code{equal}.
|
||||
ANSI says that doing @code{defconstant} of the same symbol more than once
|
||||
is undefined unless the new value is @code{eql} to the old value.
|
||||
Conforming to this specification is a nuisance when the "constant"
|
||||
value is only constant under some weaker test like @code{string=} or @code{equal}.
|
||||
|
||||
It's especially annoying because, in SBCL, @code{defconstant} takes
|
||||
effect not only at load time but also at compile time, so that just
|
||||
It's especially annoying because, in SBCL, @code{defconstant} takes effect
|
||||
not only at load time but also at compile time, so that just
|
||||
compiling and loading reasonable code like
|
||||
@lisp
|
||||
|
||||
@example
|
||||
(defconstant +foobyte+ '(1 4))
|
||||
@end lisp
|
||||
runs into this undefined behavior. Many implementations of Common Lisp
|
||||
try to help the programmer around this annoyance by silently accepting
|
||||
the undefined code and trying to do what the programmer probably
|
||||
meant.
|
||||
@end example
|
||||
|
||||
runs into this undefined behavior. Many implementations of Common
|
||||
Lisp try to help the programmer around this annoyance by silently
|
||||
accepting the undefined code and trying to do what the programmer
|
||||
probably meant.
|
||||
|
||||
SBCL instead treats the undefined behavior as an error. Often such
|
||||
code can be rewritten in portable ANSI Common Lisp which has the
|
||||
desired behavior. E.g., the code above can be given an exactly defined
|
||||
meaning by replacing @code{defconstant} either with
|
||||
@code{defparameter} or with a customized macro which does the right
|
||||
thing, e.g.
|
||||
@lisp
|
||||
desired behavior. E.g., the code above can be given an exactly
|
||||
defined meaning by replacing @code{defconstant} either with @code{defparameter} or
|
||||
with a customized macro which does the right thing, e.g.
|
||||
|
||||
@example
|
||||
(defmacro define-constant (name value &optional doc)
|
||||
`(defconstant ,name (if (boundp ',name) (symbol-value ',name) ,value)
|
||||
,@@(when doc (list doc))))
|
||||
@end lisp
|
||||
or possibly along the lines of the @code{defconstant-eqx} macro used
|
||||
internally in the implementation of SBCL itself. In circumstances
|
||||
where this is not appropriate, the programmer can handle the condition
|
||||
type @code{sb-ext:defconstant-uneql}, and choose either the
|
||||
@command{continue} or @command{abort} restart as appropriate.
|
||||
@end example
|
||||
|
||||
@node Style Warnings
|
||||
@comment node-name, next, previous, up
|
||||
or possibly along the lines of the @code{sb-int:defconstant-eqx} macro used
|
||||
internally in the implementation of SBCL itself. In circumstances
|
||||
where this is not appropriate, the programmer can handle the
|
||||
condition type @code{sb-ext:defconstant-uneql} and choose either the
|
||||
@code{continue} restart or @code{abort} restart as appropriate.
|
||||
|
||||
@node style warnings
|
||||
@subsection Style Warnings
|
||||
|
||||
SBCL gives style warnings about various kinds of perfectly legal code,
|
||||
e.g.
|
||||
|
||||
@itemize
|
||||
@item multiple @code{defun}s of the same symbol in different units;
|
||||
|
||||
@item
|
||||
multiple @code{defun}s of the same symbol in different units;
|
||||
|
||||
@item
|
||||
special variables not named in the conventional @code{*foo*} style,
|
||||
and lexical variables unconventionally named in the @code{*foo*} style
|
||||
|
||||
@item special variables not named in the conventional @code{*foo*} style, and
|
||||
lexical variables unconventionally named in the @code{*foo*} style.
|
||||
@end itemize
|
||||
|
||||
This causes friction with people who point out that other ways of
|
||||
organizing code (especially avoiding the use of @code{defgeneric}) are
|
||||
just as aesthetically stylish. However, these warnings should be read
|
||||
not as ``warning, bad aesthetics detected, you have no style'' but
|
||||
``warning, this style keeps the compiler from understanding the code
|
||||
as well as you might like.'' That is, unless the compiler warns about
|
||||
organizing code (especially avoiding the use of @code{defgeneric}) are just
|
||||
as aesthetically stylish. However, these warnings should be read not
|
||||
as @emph{warning, bad aesthetics detected, you have no style} but as
|
||||
@emph{warning, this style keeps the compiler from understanding the code
|
||||
as well as you might like}. That is, unless the compiler warns about
|
||||
such conditions, there's no way for the compiler to warn about some
|
||||
programming errors which would otherwise be easy to overlook. (Related
|
||||
bug: The warning about multiple @code{defun}s is pointlessly annoying
|
||||
when you compile and then load a function containing @code{defun}
|
||||
wrapped in @code{eval-when}, and ideally should be suppressed in that
|
||||
case, but still isn't as of SBCL 0.7.6.)
|
||||
programming errors which would otherwise be easy to
|
||||
overlook. (Related bug: The warning about multiple @code{defun}s is
|
||||
pointlessly annoying when you compile and then load a function
|
||||
containing @code{defun} wrapped in @code{eval-when}, and ideally should be
|
||||
suppressed in that case, but still isn't as of SBCL 0.7.6.)
|
||||
|
||||
|
||||
|
||||
|
||||
@node Development Tools
|
||||
@comment node-name, next, previous, up
|
||||
@node development tools
|
||||
@section Development Tools
|
||||
|
||||
@menu
|
||||
* Editor Integration::
|
||||
* Language Reference::
|
||||
* Generating Executables::
|
||||
* Editor Integration: editor integration.
|
||||
* Language Reference: language reference.
|
||||
* Generating Executables: generating executables.
|
||||
@end menu
|
||||
|
||||
@node Editor Integration
|
||||
@comment node-name, next, previous, up
|
||||
@node editor integration
|
||||
@subsection Editor Integration
|
||||
|
||||
Though SBCL can be used running ``bare'', the recommended mode of
|
||||
Though SBCL can be used running "bare", the recommended mode of
|
||||
development is with an editor connected to SBCL, supporting not
|
||||
only basic lisp editing (paren-matching, etc), but providing among
|
||||
other features an integrated debugger, interactive compilation, and
|
||||
automated documentation lookup.
|
||||
|
||||
Currently @dfn{SLIME}@footnote{Historically, the ILISP package at
|
||||
@uref{http://ilisp.cons.org/} provided similar functionality, but it
|
||||
does not support modern SBCL versions.} (Superior Lisp Interaction
|
||||
Mode for Emacs) together with Emacs is recommended for use with
|
||||
SBCL, though other options exist as well.
|
||||
Currently @emph{SLIME} (Superior Lisp Interaction Mode for Emacs)
|
||||
together with Emacs is recommended for use with SBCL, though other
|
||||
options exist as well. Historically, the ILISP package at
|
||||
@url{http://ilisp.cons.org/} provided similar functionality, but it does
|
||||
not support modern SBCL versions.
|
||||
|
||||
SLIME can be downloaded from
|
||||
@uref{https://slime.common-lisp.dev/}.
|
||||
SLIME can be downloaded from @url{https://slime.common-lisp.dev/}.
|
||||
|
||||
@node Language Reference
|
||||
@comment node-name, next, previous, up
|
||||
@node language reference
|
||||
@subsection Language Reference
|
||||
|
||||
@dfn{CLHS} (Common Lisp Hyperspec) is a hypertext version of the ANSI
|
||||
standard, made freely available by @emph{LispWorks} -- an invaluable
|
||||
@emph{CLHS} (Common Lisp Hyperspec) is a hypertext version of the ANSI
|
||||
standard, made freely available by LispWorks -- an invaluable
|
||||
reference.
|
||||
|
||||
See: @uref{https://www.lispworks.com/documentation/HyperSpec/Front/index.htm}
|
||||
See @url{https://www.lispworks.com/documentation/HyperSpec/Front/index.htm}.
|
||||
|
||||
@node Generating Executables
|
||||
@comment node-name, next, previous, up
|
||||
@node generating executables
|
||||
@subsection Generating Executables
|
||||
|
||||
SBCL can generate stand-alone executables. The generated executables
|
||||
include the SBCL runtime itself, so no restrictions are placed on
|
||||
program functionality. For example, a deployed program can call
|
||||
@code{compile} and @code{load}, which requires the compiler to be present
|
||||
in the executable. For further information, @xref{Function
|
||||
sb-ext save-lisp-and-die}.
|
||||
@code{compile} and @code{load}, which requires the compiler to be present in the
|
||||
executable. For further information, @code{sb-ext:save-lisp-and-die}.
|
||||
|
||||
|
||||
@node More SBCL Information
|
||||
@comment node-name, next, previous, up
|
||||
@node more sbcl information
|
||||
@section More SBCL Information
|
||||
|
||||
@menu
|
||||
* SBCL Homepage::
|
||||
* Online Documentation::
|
||||
* Additional Documentation Files::
|
||||
* Internals Documentation::
|
||||
* SBCL Homepage: sbcl homepage.
|
||||
* Online Documentation: online documentation.
|
||||
* Additional Documentation Files: additional documentation files.
|
||||
* Internals Documentation: internals documentation.
|
||||
@end menu
|
||||
|
||||
@node SBCL Homepage
|
||||
@comment node-name, next, previous, up
|
||||
@node sbcl homepage
|
||||
@subsection SBCL Homepage
|
||||
|
||||
The SBCL website at @uref{http://www.sbcl.org/} has some general
|
||||
The SBCL website at @url{http://www.sbcl.org/} has some general
|
||||
information, plus links to mailing lists devoted to SBCL, and to
|
||||
archives of these mailing lists. Subscribing to the mailing lists
|
||||
@cite{sbcl-help} and @cite{sbcl-announce} is recommended: both are
|
||||
fairly low-volume, and help you keep abreast with SBCL development.
|
||||
@code{sbcl-help} and @code{sbcl-announce} is recommended: both are fairly
|
||||
low-volume, and help you keep abreast with SBCL development.
|
||||
|
||||
@node Online Documentation
|
||||
@comment node-name, next, previous, up
|
||||
@node online documentation
|
||||
@subsection Online Documentation
|
||||
|
||||
Documentation for non-ANSI extensions for various commands is
|
||||
available online from the SBCL executable itself. The extensions
|
||||
for functions which have their own command prompts (e.g. the debugger,
|
||||
and @code{inspect}) are documented in text available by typing
|
||||
@command{help} at their command prompts. The extensions for functions
|
||||
which don't have their own command prompt (such as @code{trace}) are
|
||||
described in their documentation strings, unless your SBCL was
|
||||
compiled with an option not to include documentation strings, in which
|
||||
case the documentation strings are only readable in the source code.
|
||||
available online from the SBCL executable itself. The extensions for
|
||||
functions which have their own command prompts (e.g. the debugger,
|
||||
and @code{inspect}) are documented in text available by typing @code{help} at
|
||||
their command prompts. The extensions for functions which don't have
|
||||
their own command prompt (such as @code{trace}) are described in their
|
||||
documentation strings, unless your SBCL was compiled with an option
|
||||
not to include documentation strings, in which case the
|
||||
documentation strings are only readable in the source code.
|
||||
|
||||
@node Additional Documentation Files
|
||||
@comment node-name, next, previous, up
|
||||
@node additional documentation files
|
||||
@subsection Additional Documentation Files
|
||||
|
||||
Besides this user manual both SBCL source and binary distributions
|
||||
include some other SBCL-specific documentation files, which should be
|
||||
installed along with this manual on your system, e.g. in
|
||||
@file{/usr/local/share/doc/sbcl/}.
|
||||
include some other SBCL-specific documentation files, which should
|
||||
be installed along with this manual on your system, e.g. in
|
||||
@code{/usr/local/share/doc/sbcl/}.
|
||||
|
||||
@table @file
|
||||
@itemize
|
||||
@item @code{copying}: Licence and copyright summary.
|
||||
|
||||
@item COPYING
|
||||
Licence and copyright summary.
|
||||
@item @code{credits}: Authorship information on various parts of SBCL.
|
||||
|
||||
@item CREDITS
|
||||
Authorship information on various parts of SBCL.
|
||||
@item @code{install}: Covers installing SBCL from both source and binary
|
||||
distributions on your system, and also has some installation
|
||||
related troubleshooting information.
|
||||
|
||||
@item INSTALL
|
||||
Covers installing SBCL from both source and binary distributions on
|
||||
your system, and also has some installation related troubleshooting
|
||||
information.
|
||||
@item @code{news}: Summarizes changes between various SBCL versions.
|
||||
@end itemize
|
||||
|
||||
@item NEWS
|
||||
Summarizes changes between various SBCL versions.
|
||||
|
||||
@end table
|
||||
|
||||
@node Internals Documentation
|
||||
@comment node-name, next, previous, up
|
||||
@node internals documentation
|
||||
@subsection Internals Documentation
|
||||
|
||||
If you're interested in the development of the SBCL system itself,
|
||||
then subscribing to @cite{sbcl-devel} is a good idea.
|
||||
|
||||
@c FIXME: Copy historical info from the Web Archive to ... somewhere?
|
||||
then subscribing to @code{sbcl-devel} is a good idea.
|
||||
|
||||
SBCL internals documentation -- besides comments in the source -- is
|
||||
available
|
||||
@uref{https://web.archive.org/web/20120814000933/http://sbcl-internals.cliki.net/index,in
|
||||
the Web Archive}.
|
||||
available in the Web Archive:
|
||||
|
||||
@url{https://web.archive.org/web/20120814000933/http://sbcl-internals.cliki.net/index}.
|
||||
|
||||
Some low-level information describing the programming details of the
|
||||
conversion from CMUCL to SBCL is available in the
|
||||
@file{doc/FOR-CMUCL-DEVELOPERS} file in the SBCL distribution and
|
||||
@uref{https://sourceforge.net/p/sbcl/sbcl/ci/master/tree/doc/FOR-CMUCL-DEVELOPERS,on
|
||||
SourceForge}.
|
||||
@code{doc/FOR-CMUCL-DEVELOPERS} file.
|
||||
|
||||
@node More Common Lisp Information
|
||||
@comment node-name, next, previous, up
|
||||
@node more common lisp information
|
||||
@section More Common Lisp Information
|
||||
|
||||
@menu
|
||||
* Internet Community::
|
||||
* Third-party Libraries::
|
||||
* Common Lisp Books::
|
||||
* Internet Community: internet community.
|
||||
* Third-party Libraries: third party libraries.
|
||||
* Common Lisp Books: common lisp books.
|
||||
@end menu
|
||||
|
||||
@node Internet Community
|
||||
@comment node-name, next, previous, up
|
||||
@node internet community
|
||||
@subsection Internet Community
|
||||
|
||||
@c FIXME: Say something smart here
|
||||
IRC channels on @url{https://libera.chat/}:
|
||||
|
||||
The Common Lisp internet community is fairly diverse:
|
||||
@uref{https://groups.google.com/g/comp.lang.lisp} is fairly high volume newsgroup, but has
|
||||
a rather poor signal/noise ratio. Various special interest mailing
|
||||
lists and IRC tend to provide more content and less flames.
|
||||
@uref{https://www.lisp.org} and @uref{https://cliki.net} contain
|
||||
@itemize
|
||||
@item @code{#common-lisp}: "Common Lisp, the #1=(programmable . #1#)
|
||||
programming language"
|
||||
|
||||
@item @code{#lispcafe}: "The Lisp Café; sit down, have a drink, chat about
|
||||
anything, and enjoy your stay. | @url{https://www.cliki.net/lispcafe} |
|
||||
Be insuperable to each other".
|
||||
|
||||
@item @code{#sbcl}: "Steel Bank Common Lisp Dev Hangout"
|
||||
@end itemize
|
||||
|
||||
You can use @url{https://web.libera.chat} or a normal IRC client.
|
||||
|
||||
Also, see @url{https://www.reddit.com/r/Common_Lisp/}, as well as
|
||||
@url{https://www.lisp.org} and @url{https://cliki.net}, which contain
|
||||
numerous pointers places in the net where lispers talks shop.
|
||||
|
||||
@node Third-party Libraries
|
||||
@comment node-name, next, previous, up
|
||||
@node third party libraries
|
||||
@subsection Third-party Libraries
|
||||
|
||||
For a wealth of information about free Common Lisp libraries and tools
|
||||
we recommend checking out @emph{CLiki}: @uref{https://cliki.net/}.
|
||||
we recommend checking out @emph{CLiki}: @url{https://cliki.net/}.
|
||||
|
||||
@node Common Lisp Books
|
||||
@comment node-name, next, previous, up
|
||||
The most popular library manager is Quicklisp:
|
||||
@url{https://www.quicklisp.org/beta/}.
|
||||
|
||||
@node common lisp books
|
||||
@subsection Common Lisp Books
|
||||
|
||||
If you're not a programmer and you're trying to learn, many
|
||||
introductory Lisp books are available. However, we don't have any
|
||||
standout favorites. If you can't decide, try checking the Usenet
|
||||
@uref{https://groups.google.com/g/comp.lang.lisp} FAQ for recent
|
||||
recommendations.
|
||||
|
||||
@c FIXME: This non-stance is silly. Maybe we could recommend SICP,
|
||||
@c Touretzky, or something at least.
|
||||
standout favorites.
|
||||
|
||||
If you are an experienced programmer in other languages but need to
|
||||
learn about Common Lisp, some books stand out:
|
||||
|
||||
@table @cite
|
||||
|
||||
@itemize
|
||||
@item Practical Common Lisp, by Peter Seibel
|
||||
An excellent introduction to the language, covering both the basics
|
||||
and ``advanced topics'' like macros, CLOS, and packages. Available
|
||||
both in print format and on the web: @uref{https://gigamonkeys.com/book/}.
|
||||
|
||||
An excellent introduction to the language, covering both the
|
||||
basics and "advanced topics" like macros, CLOS, and packages.
|
||||
Available both in print format and on the web:
|
||||
@url{https://gigamonkeys.com/book/}.
|
||||
|
||||
@item Paradigms Of Artificial Intelligence Programming, by Peter Norvig
|
||||
|
||||
Good information on general Common Lisp programming, and many
|
||||
nontrivial examples. Whether or not your work is AI, it's a very good
|
||||
book to look at.
|
||||
nontrivial examples. Whether or not your work is AI, it's a very
|
||||
good book to look at.
|
||||
|
||||
@item On Lisp, by Paul Graham
|
||||
An in-depth treatment of macros, but not recommended as a first Common
|
||||
Lisp book, since it is slightly pre-ANSI so you need to be on your
|
||||
guard against non-standard usages, and since it doesn't really even
|
||||
try to cover the language as a whole, focusing solely on macros.
|
||||
Downloadable from @uref{https://www.paulgraham.com/onlisp.html}.
|
||||
|
||||
An in-depth treatment of macros, but not recommended as a first
|
||||
Common Lisp book, since it is slightly pre-ANSI so you need to
|
||||
be on your guard against non-standard usages, and since it
|
||||
doesn't really even try to cover the language as a whole,
|
||||
focusing solely on macros. Downloadable from
|
||||
@url{https://www.paulgraham.com/onlisp.html}.
|
||||
|
||||
@item Object-Oriented Programming In Common Lisp, by Sonya Keene
|
||||
With the exception of @cite{Practical Common Lisp} most introductory
|
||||
|
||||
With the exception of @emph{Practical Common Lisp}, most introductory
|
||||
books don't emphasize CLOS. This one does. Even if you're very
|
||||
knowledgeable about object oriented programming in the abstract, it's
|
||||
worth looking at this book if you want to do any OO in Common Lisp.
|
||||
Some abstractions in CLOS (especially multiple dispatch) go beyond
|
||||
anything you'll see in most OO systems, and there are a number of
|
||||
lesser differences as well. This book tends to help with the culture
|
||||
shock.
|
||||
knowledgeable about object oriented programming in the abstract,
|
||||
it's worth looking at this book if you want to do any OO in
|
||||
Common Lisp. Some abstractions in CLOS (especially multiple
|
||||
dispatch) go beyond anything you'll see in most OO systems, and
|
||||
there are a number of lesser differences as well. This book
|
||||
tends to help with the culture shock.
|
||||
|
||||
@item Art Of Metaobject Programming, by Gregor Kiczales et al.
|
||||
Currently the prime source of information on the Common Lisp Metaobject
|
||||
Protocol, which is supported by SBCL. Section 2 (Chapters 5 and 6) are
|
||||
freely available at @uref{http://mop.lisp.se/www.alu.org/mop/}.
|
||||
|
||||
@end table
|
||||
Currently the prime source of information on the Common Lisp
|
||||
Metaobject Protocol, which is supported by SBCL. Section
|
||||
2 (Chapters 5 and 6) are freely available at
|
||||
@url{http://mop.lisp.se/www.alu.org/mop/}.
|
||||
@end itemize
|
||||
|
||||
|
||||
|
||||
|
||||
@node History and Implementation of SBCL
|
||||
@comment node-name, next, previous, up
|
||||
@node history and implementation of sbcl
|
||||
@section History and Implementation of SBCL
|
||||
|
||||
You can work productively with SBCL without knowing or
|
||||
understanding anything about where it came from, how it is
|
||||
implemented, or how it extends the ANSI Common Lisp standard. However,
|
||||
a little knowledge can be helpful in order to understand error
|
||||
messages, to troubleshoot problems, to understand why some parts of
|
||||
the system are better debugged than others, and to anticipate which
|
||||
known bugs, known performance problems, and missing extensions are
|
||||
likely to be fixed, tuned, or added.
|
||||
You can work productively with SBCL without knowing or understanding
|
||||
anything about where it came from, how it is implemented, or how it
|
||||
extends the ANSI Common Lisp standard. However, a little knowledge
|
||||
can be helpful in order to understand error messages, to
|
||||
troubleshoot problems, to understand why some parts of the system
|
||||
are better debugged than others, and to anticipate which known bugs,
|
||||
known performance problems, and missing extensions are likely to be
|
||||
fixed, tuned, or added.
|
||||
|
||||
SBCL is descended from CMUCL, which is itself descended from Spice
|
||||
Lisp, including early implementations for the Mach operating system on
|
||||
|
|
@ -556,47 +492,40 @@ the IBM RT, back in the 1980s. Some design decisions from that time are
|
|||
still reflected in the current implementation:
|
||||
|
||||
@itemize
|
||||
@item The system expects to be loaded into a fixed-at-compile-time
|
||||
location in virtual memory, and also expects the location of all
|
||||
of its heap storage to be specified at compile time.
|
||||
|
||||
@item
|
||||
The system expects to be loaded into a fixed-at-compile-time location
|
||||
in virtual memory, and also expects the location of all of its heap
|
||||
storage to be specified at compile time.
|
||||
|
||||
@item
|
||||
The system overcommits memory, allocating large amounts of address
|
||||
space from the system (often more than the amount of virtual memory
|
||||
available) and then failing if it ends up using too much of the
|
||||
allocated storage.
|
||||
|
||||
@item
|
||||
The system is implemented as a C program which is responsible for
|
||||
supplying low-level services and loading a Lisp @file{.core}
|
||||
file.
|
||||
@item The system overcommits memory, allocating large amounts of address
|
||||
space from the system (often more than the amount of virtual
|
||||
memory available) and then failing if it ends up using too much of
|
||||
the allocated storage.
|
||||
|
||||
@item The system is implemented as a C program which is responsible for
|
||||
supplying low-level services and loading a Lisp @code{.core} file.
|
||||
@end itemize
|
||||
|
||||
@cindex Garbage Collection, generational
|
||||
SBCL also inherited some newer architectural features from CMUCL. The
|
||||
most important is that on some architectures it has a generational
|
||||
garbage collector (``GC''), which has various implications (mostly
|
||||
good) for performance. These are discussed in another chapter,
|
||||
@ref{Efficiency}.
|
||||
SBCL also inherited some newer architectural features from CMUCL.
|
||||
The most important is that on some architectures it has a
|
||||
generational garbage collector (GC), which has various
|
||||
implications (mostly good) for performance. These are discussed in
|
||||
another chapter, @ref{efficiency}.
|
||||
|
||||
SBCL has diverged from CMUCL in that SBCL is now essentially a
|
||||
``compiler-only implementation'' of Common Lisp. This is a change in
|
||||
implementation strategy, taking advantage of the freedom ``any of these
|
||||
facilities might share the same execution strategy'' guaranteed in the
|
||||
ANSI specification section 3.1 (``Evaluation''). It does not mean SBCL
|
||||
can't be used interactively, and in fact the change is largely invisible
|
||||
compiler-only implementation of Common Lisp. This is a change in
|
||||
implementation strategy, taking advantage of the freedom "any of
|
||||
these facilities might share the same execution strategy"
|
||||
guaranteed in @code{clhs} @code{3.1} (Evaluation). It does not mean SBCL can't
|
||||
be used interactively, and in fact the change is largely invisible
|
||||
to the casual user, since SBCL still can and does execute code
|
||||
interactively by compiling it on the fly. (It is visible if you know how
|
||||
to look, like using @code{compiled-function-p}; and it is visible in the
|
||||
way that SBCL doesn't have many bugs which behave differently in
|
||||
interpreted code than in compiled code.) What it means is that in SBCL,
|
||||
the @code{eval} function only truly ``interprets'' a few easy kinds of
|
||||
forms, such as symbols which are @code{boundp}. More complicated forms
|
||||
are evaluated by calling @code{compile} and then calling @code{funcall}
|
||||
on the returned result.
|
||||
interactively by compiling it on the fly. (It is visible if you know
|
||||
how to look, like using @code{compiled-function-p}; and it is visible in
|
||||
the way that SBCL doesn't have many bugs which behave differently in
|
||||
interpreted code than in compiled code.) What it means is that in
|
||||
SBCL, the @code{eval} function only truly "interprets" a few easy kinds
|
||||
of forms, such as symbols which are @code{boundp}. More complicated forms
|
||||
are evaluated by calling @code{compile} and then calling @code{funcall} on the
|
||||
returned result.
|
||||
|
||||
The direct ancestor of SBCL is the x86 port of CMUCL. This port was in
|
||||
some ways the most cobbled-together of all the CMUCL ports, since a
|
||||
|
|
@ -605,7 +534,6 @@ x86 architecture. Some things (like tracing and debugging) do not work
|
|||
particularly well there. SBCL should be able to improve in these areas
|
||||
(and has already improved in some other areas), but it takes a while.
|
||||
|
||||
@cindex Garbage Collection, conservative
|
||||
On the x86 SBCL -- like the x86 port of CMUCL -- uses a
|
||||
@emph{conservative} GC. This means that it doesn't maintain a strict
|
||||
separation between tagged and untagged data, instead treating some
|
||||
|
|
@ -613,39 +541,36 @@ untagged data (e.g. raw floating point numbers) as possibly-tagged
|
|||
data and so not collecting any Lisp objects that they point to. This
|
||||
has some negative consequences for average time efficiency (though
|
||||
possibly no worse than the negative consequences of trying to
|
||||
implement an exact GC on a processor architecture as register-poor as
|
||||
the X86) and also has potentially unlimited consequences for
|
||||
implement an exact GC on a processor architecture as register-poor
|
||||
as the X86) and also has potentially unlimited consequences for
|
||||
worst-case memory efficiency. In practice, conservative garbage
|
||||
collectors work reasonably well, not getting anywhere near the worst
|
||||
case. But they can occasionally cause odd patterns of memory usage.
|
||||
|
||||
The fork from CMUCL was based on a major rewrite of the system
|
||||
bootstrap process. CMUCL has for many years tolerated a very unusual
|
||||
``build'' procedure which doesn't actually build the complete system
|
||||
from scratch, but instead progressively overwrites parts of a running
|
||||
system with new versions. This quasi-build procedure can cause various
|
||||
bizarre bootstrapping hangups, especially when a major change is made
|
||||
to the system. It also makes the connection between the current source
|
||||
code and the current executable more tenuous than in other software
|
||||
systems -- it's easy to accidentally ``build'' a CMUCL system
|
||||
containing characteristics not reflected in the current version of the
|
||||
source code.
|
||||
"build" procedure which doesn't actually build the complete system
|
||||
from scratch, but instead progressively overwrites parts of a
|
||||
running system with new versions. This quasi-build procedure can
|
||||
cause various bizarre bootstrapping hangups, especially when a major
|
||||
change is made to the system. It also makes the connection between
|
||||
the current source code and the current executable more tenuous than
|
||||
in other software systems -- it's easy to accidentally build a CMUCL
|
||||
system containing characteristics not reflected in the current
|
||||
version of the source code.
|
||||
|
||||
Other major changes since the fork from CMUCL include
|
||||
Other major changes since the fork from CMUCL include:
|
||||
|
||||
@itemize
|
||||
@item SBCL has removed many CMUCL extensions, (e.g. IP networking,
|
||||
remote procedure call, Unix system interface, and X11 interface)
|
||||
from the core system. Most of these are available as contributed
|
||||
modules (distributed with SBCL) or third-party modules instead.
|
||||
|
||||
@item
|
||||
SBCL has removed many CMUCL extensions, (e.g. IP networking,
|
||||
remote procedure call, Unix system interface, and X11 interface) from
|
||||
the core system. Most of these are available as contributed modules
|
||||
(distributed with SBCL) or third-party modules instead.
|
||||
|
||||
@item
|
||||
SBCL has deleted or deprecated some nonstandard features and code
|
||||
complexity which helped efficiency at the price of
|
||||
maintainability. For example, the SBCL compiler no longer implements
|
||||
memory pooling internally (and so is simpler and more maintainable,
|
||||
but generates more garbage and runs more slowly).
|
||||
|
||||
@item SBCL has deleted or deprecated some nonstandard features and code
|
||||
complexity which helped efficiency at the price of
|
||||
maintainability. For example, the SBCL compiler no longer
|
||||
implements memory pooling internally (and so is simpler and more
|
||||
maintainable, but generates more garbage and runs more slowly).
|
||||
@end itemize
|
||||
|
||||
|
|
|
|||
|
|
@ -1,58 +1,49 @@
|
|||
@node Package Locks
|
||||
@comment node-name, next, previous, up
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node package locks
|
||||
@chapter Package Locks
|
||||
@cindex Packages, locked
|
||||
|
||||
@menu
|
||||
* Package Lock Concepts: package lock concepts.
|
||||
* Package Lock Dictionary: package lock dictionary.
|
||||
@end menu
|
||||
|
||||
None of the following sections apply to SBCL built without package
|
||||
locking support.
|
||||
|
||||
@quotation warning
|
||||
The interface described here is experimental: incompatible changes in
|
||||
future SBCL releases are possible, even expected: the concept of
|
||||
``implementation packages'' and the associated operators may be renamed;
|
||||
more operations (such as naming restarts or catch tags) may be added to
|
||||
the list of operations violating package locks.
|
||||
@end quotation
|
||||
The interface described here is experimental: incompatible changes
|
||||
in future SBCL releases are possible, even expected: the concept of
|
||||
@emph{implementation packages} and the associated operators may be
|
||||
renamed; more operations (such as naming restarts or catch tags) may
|
||||
be added to the list of operations violating package locks.
|
||||
|
||||
@menu
|
||||
* Package Lock Concepts::
|
||||
* Package Lock Dictionary::
|
||||
@end menu
|
||||
|
||||
@node Package Lock Concepts
|
||||
@node package lock concepts
|
||||
@section Package Lock Concepts
|
||||
|
||||
@menu
|
||||
* Package Lock Overview::
|
||||
* Implementation Packages::
|
||||
* Package Lock Violations::
|
||||
* Package Locks in Compiled Code::
|
||||
* Operations Violating Package Locks::
|
||||
* Implementation Packages: implementation packages.
|
||||
* Package Lock Violations: package lock violations.
|
||||
* Package Locks in Compiled Code: package locks in compiled code.
|
||||
* Operations Violating Package Locks: operations violating package locks.
|
||||
@end menu
|
||||
|
||||
@node Package Lock Overview
|
||||
@comment node-name, next, previous, up
|
||||
@subsection Package Locking Overview
|
||||
|
||||
Package locks protect against unintentional modifications of a package:
|
||||
they provide similar protection to user packages as is mandated to
|
||||
@code{common-lisp} package by the ANSI specification. They are not, and
|
||||
should not be used as, a security measure.
|
||||
|
||||
Newly created packages are by default unlocked (see the @code{:lock}
|
||||
option to @code{defpackage}).
|
||||
Newly created packages are by default unlocked (see the @code{:lock} option
|
||||
to @code{defpackage}).
|
||||
|
||||
The package @code{common-lisp} and SBCL internal implementation
|
||||
packages are locked by default, including @code{sb-ext}.
|
||||
The package @code{common-lisp} and SBCL internal implementation packages
|
||||
are locked by default, including @code{sb-ext}.
|
||||
|
||||
It may be beneficial to lock @code{common-lisp-user} as well, to
|
||||
ensure that various libraries don't pollute it without asking,
|
||||
but this is not currently done by default.
|
||||
It may be beneficial to lock @code{common-lisp-user} as well, to ensure
|
||||
that various libraries don't pollute it without asking, but this is
|
||||
not currently done by default.
|
||||
|
||||
@node Implementation Packages
|
||||
@node implementation packages
|
||||
@subsection Implementation Packages
|
||||
@vindex @cl{@earmuffs{package}}
|
||||
@findex @cl{defpackage}
|
||||
|
||||
Each package has a list of associated implementation packages. A
|
||||
locked package, and the symbols whose home package it is, can be
|
||||
|
|
@ -64,40 +55,32 @@ Unless explicitly altered by @code{defpackage},
|
|||
@code{sb-ext:remove-implementation-package} each package is its own
|
||||
(only) implementation package.
|
||||
|
||||
@node Package Lock Violations
|
||||
@node package lock violations
|
||||
@subsection Package Lock Violations
|
||||
@tindex @sbext{package-lock-violation}
|
||||
@tindex @sbext{package-locked-error}
|
||||
@tindex @sbext{symbol-package-locked-error}
|
||||
@tindex @cl{package-error}
|
||||
|
||||
@menu
|
||||
* Lexical Bindings and Declarations: lexical bindings and declarations.
|
||||
* Other Operations: other operations.
|
||||
@end menu
|
||||
|
||||
@node lexical bindings and declarations
|
||||
@subsubsection Lexical Bindings and Declarations
|
||||
@findex @cl{let}
|
||||
@findex @cl{let*}
|
||||
@findex @cl{flet}
|
||||
@findex @cl{labels}
|
||||
@findex @cl{macrolet}
|
||||
@findex @cl{symbol-macrolet}
|
||||
@findex @cl{declare}
|
||||
@cindex Declarations
|
||||
@findex @sbext{disable-package-locks}
|
||||
@findex @sbext{enable-package-locks}
|
||||
|
||||
Lexical bindings or declarations that violate package locks cause a
|
||||
compile-time warning, and a runtime @code{program-error} when the form
|
||||
that violates package locks would be executed.
|
||||
compile-time warning, and a runtime @code{program-error} when the form that
|
||||
violates package locks would be executed.
|
||||
|
||||
A complete listing of operators affect by this is: @code{let},
|
||||
@code{let*}, @code{flet}, @code{labels}, @code{macrolet}, and
|
||||
@code{symbol-macrolet}, @code{declare}.
|
||||
A complete listing of operators affect by this is: @code{let}, @code{let*}, @code{flet},
|
||||
@code{labels}, @code{macrolet}, and @code{symbol-macrolet}, @code{declare}.
|
||||
|
||||
Package locks affecting both lexical bindings and declarations can be
|
||||
disabled locally with @code{sb-ext:disable-package-locks} declaration,
|
||||
and re-enabled with @code{sb-ext:enable-package-locks} declaration.
|
||||
Package locks affecting both lexical bindings and declarations can
|
||||
be disabled locally with the @code{sb-ext:disable-package-locks}
|
||||
declaration, and re-enabled with the @code{sb-ext:enable-package-locks}
|
||||
declaration.
|
||||
|
||||
Example:
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(in-package :locked)
|
||||
|
||||
(defun foo () ...)
|
||||
|
|
@ -107,8 +90,9 @@ Example:
|
|||
(flet ((foo () ...))
|
||||
(declare (enable-package-locks locked:foo)) ; re-enable for body
|
||||
,@@body)))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
@node other operations
|
||||
@subsubsection Other Operations
|
||||
|
||||
If an non-lexical operation violates a package lock, a continuable
|
||||
|
|
@ -119,87 +103,79 @@ attempted.
|
|||
Additional restarts may be established for continuable package lock
|
||||
violations for interactive use.
|
||||
|
||||
The actual type of the error depends on circumstances that caused the
|
||||
violation: operations on packages signal errors of type
|
||||
@code{sb-ext:package-locked-error}, and operations on symbols signal
|
||||
errors of type @code{sb-ext:symbol-package-locked-error}.
|
||||
The actual type of the error depends on circumstances that caused
|
||||
the violation: operations on packages signal errors of type
|
||||
@code{sb-ext:package-locked-error}, and operations on symbols signal errors
|
||||
of type @code{sb-ext:symbol-package-locked-error}.
|
||||
|
||||
|
||||
@node Package Locks in Compiled Code
|
||||
@node package locks in compiled code
|
||||
@subsection Package Locks in Compiled Code
|
||||
|
||||
@subsubsection Interned Symbols
|
||||
|
||||
If file-compiled code contains interned symbols, then loading that code
|
||||
into an image without the said symbols will not cause a package lock
|
||||
violation, even if the packages in question are locked.
|
||||
|
||||
@subsubsection Other Limitations on Compiled Code
|
||||
If file-compiled code contains interned symbols, then loading that
|
||||
code into an image without the said symbols will not cause a package
|
||||
lock violation, even if the packages in question are locked.
|
||||
|
||||
With the exception of interned symbols, behaviour is unspecified if
|
||||
package locks affecting compiled code are not the same during loading
|
||||
of the code or execution.
|
||||
package locks affecting compiled code are not the same during
|
||||
loading of the code or execution.
|
||||
|
||||
Specifically, code compiled with packages unlocked may or may not fail
|
||||
to signal package-lock-violations even if the packages are locked at
|
||||
runtime, and code compiled with packages locked may or may not signal
|
||||
spurious package-lock-violations at runtime even if the packages are
|
||||
unlocked.
|
||||
Specifically, code compiled with packages unlocked may or may not
|
||||
fail to signal package-lock-violations even if the packages are
|
||||
locked at runtime, and code compiled with packages locked may or may
|
||||
not signal spurious package-lock-violations at runtime even if the
|
||||
packages are unlocked.
|
||||
|
||||
In practice all this means that package-locks have a negligible
|
||||
performance penalty in compiled code as long as they are not violated.
|
||||
performance penalty in compiled code as long as they are not
|
||||
violated.
|
||||
|
||||
@node Operations Violating Package Locks
|
||||
@node operations violating package locks
|
||||
@subsection Operations Violating Package Locks
|
||||
|
||||
@menu
|
||||
* Operations on Packages: operations on packages.
|
||||
* Operations on Symbols: operations on symbols.
|
||||
@end menu
|
||||
|
||||
@node operations on packages
|
||||
@subsubsection Operations on Packages
|
||||
|
||||
The following actions cause a package lock violation if the package
|
||||
operated on is locked, and @code{*package*} is not an implementation
|
||||
package of that package, and the action would cause a change in the
|
||||
state of the package (so e.g. exporting already external symbols is
|
||||
never a violation). Package lock violations caused by these operations
|
||||
signal errors of type @code{sb-ext:package-locked-error}.
|
||||
never a violation). Package lock violations caused by these
|
||||
operations signal errors of type @code{sb-ext:package-locked-error}.
|
||||
|
||||
@enumerate
|
||||
@item
|
||||
Shadowing a symbol in a package.
|
||||
@itemize
|
||||
@item Shadowing a symbol in a package.
|
||||
|
||||
@item
|
||||
Importing a symbol to a package.
|
||||
@item Importing a symbol to a package.
|
||||
|
||||
@item
|
||||
Uninterning a symbol from a package.
|
||||
@item Uninterning a symbol from a package.
|
||||
|
||||
@item
|
||||
Exporting a symbol from a package.
|
||||
@item Exporting a symbol from a package.
|
||||
|
||||
@item
|
||||
Unexporting a symbol from a package.
|
||||
@item Unexporting a symbol from a package.
|
||||
|
||||
@item
|
||||
Changing the packages used by a package.
|
||||
@item Changing the packages used by a package.
|
||||
|
||||
@item
|
||||
Renaming a package.
|
||||
@item Renaming a package.
|
||||
|
||||
@item
|
||||
Deleting a package.
|
||||
@item Deleting a package.
|
||||
|
||||
@item
|
||||
Adding a new package local nickname to a package.
|
||||
@item Adding a new package local nickname to a package.
|
||||
|
||||
@item
|
||||
Removing an existing package local nickname to a package.
|
||||
|
||||
@end enumerate
|
||||
@item Removing an existing package local nickname to a package.
|
||||
@end itemize
|
||||
|
||||
@node operations on symbols
|
||||
@subsubsection Operations on Symbols
|
||||
|
||||
Following actions cause a package lock violation if the home package
|
||||
of the symbol operated on is locked, and @code{*package*} is not an
|
||||
implementation package of that package. Package lock violations caused
|
||||
by these action signal errors of type
|
||||
implementation package of that package. Package lock violations
|
||||
caused by these action signal errors of type
|
||||
@code{sb-ext:symbol-package-locked-error}.
|
||||
|
||||
These actions cause only one package lock violation per lexically
|
||||
|
|
@ -207,7 +183,8 @@ apparent violated package.
|
|||
|
||||
Example:
|
||||
|
||||
@lisp
|
||||
|
||||
@example
|
||||
;;; Packages FOO and BAR are locked.
|
||||
;;;
|
||||
;;; Two lexically apparent violated packages: exactly two
|
||||
|
|
@ -216,155 +193,194 @@ Example:
|
|||
(defclass foo:point ()
|
||||
((x :accessor bar:x)
|
||||
(y :accessor bar:y)))
|
||||
@end lisp
|
||||
|
||||
@enumerate
|
||||
@item
|
||||
Binding or altering its value lexically or dynamically, or
|
||||
establishing it as a symbol-macro.
|
||||
|
||||
Exceptions:
|
||||
|
||||
@itemize @minus
|
||||
@item
|
||||
If the symbol is not defined as a constant, global symbol-macro or a
|
||||
global dynamic variable, it may be lexically bound or established as a
|
||||
local symbol macro.
|
||||
|
||||
@item
|
||||
If the symbol is defined as a global dynamic variable, it may be
|
||||
assigned or bound.
|
||||
|
||||
@end itemize
|
||||
|
||||
@item
|
||||
Defining, undefining, or binding it, or its setf name as a function.
|
||||
|
||||
Exceptions:
|
||||
|
||||
@itemize @minus
|
||||
@item
|
||||
If the symbol is not defined as a function, macro, or special operator
|
||||
it and its setf name may be lexically bound as a function.
|
||||
|
||||
@end itemize
|
||||
|
||||
@item
|
||||
Defining, undefining, or binding it as a macro or compiler macro.
|
||||
|
||||
Exceptions:
|
||||
|
||||
@itemize @minus
|
||||
@item
|
||||
If the symbol is not defined as a function, macro, or special operator
|
||||
it may be lexically bound as a macro.
|
||||
|
||||
@end itemize
|
||||
|
||||
@item
|
||||
Defining it as a type specifier or structure.
|
||||
|
||||
@item
|
||||
Defining it as a declaration with a declaration proclamation.
|
||||
|
||||
@item
|
||||
Declaring or proclaiming it special.
|
||||
|
||||
@item
|
||||
Declaring or proclaiming its type or ftype.
|
||||
|
||||
Exceptions:
|
||||
|
||||
@itemize @minus
|
||||
@item
|
||||
If the symbol may be lexically bound, the type of that binding may be
|
||||
declared.
|
||||
|
||||
@item
|
||||
If the symbol may be lexically bound as a function, the ftype of that
|
||||
binding may be declared.
|
||||
|
||||
@end itemize
|
||||
|
||||
@item
|
||||
Defining a setf expander for it.
|
||||
|
||||
@item
|
||||
Defining it as a method combination type.
|
||||
|
||||
@item
|
||||
Using it as the class-name argument to setf of find-class.
|
||||
|
||||
@item
|
||||
Defining it as a hash table test using @code{sb-ext:define-hash-table-test}.
|
||||
|
||||
@end enumerate
|
||||
|
||||
@node Package Lock Dictionary
|
||||
@section Package Lock Dictionary
|
||||
|
||||
@deffn {Declaration} @sbext{disable-package-locks}
|
||||
|
||||
Syntax: @code{(sb-ext:disable-package-locks symbol*)}
|
||||
|
||||
Disables package locks affecting the named symbols during compilation
|
||||
in the lexical scope of the declaration. Disabling locks on symbols
|
||||
whose home package is unlocked, or disabling an already disabled lock,
|
||||
has no effect.
|
||||
@end deffn
|
||||
|
||||
@deffn {Declaration} @sbext{enable-package-locks}
|
||||
|
||||
Syntax: @code{(sb-ext:enable-package-locks symbol*)}
|
||||
|
||||
Re-enables package locks affecting the named symbols during compilation
|
||||
in the lexical scope of the declaration. Enabling locks that were not
|
||||
first disabled with @code{sb-ext:disable-package-locks} declaration, or
|
||||
enabling locks that are already enabled has no effect.
|
||||
@end deffn
|
||||
|
||||
@include condition-sb-ext-package-lock-violation.texinfo
|
||||
@include condition-sb-ext-package-locked-error.texinfo
|
||||
@include condition-sb-ext-symbol-package-locked-error.texinfo
|
||||
|
||||
@defun @sbext{package-locked-error-symbol} symbol-package-locked-error
|
||||
|
||||
Returns the symbol that caused the @code{symbol-package-locked-error}
|
||||
condition.
|
||||
@end defun
|
||||
|
||||
@include fun-sb-ext-package-locked-p.texinfo
|
||||
@include fun-sb-ext-lock-package.texinfo
|
||||
@include fun-sb-ext-unlock-package.texinfo
|
||||
@include fun-sb-ext-package-implemented-by-list.texinfo
|
||||
@include fun-sb-ext-package-implements-list.texinfo
|
||||
@include fun-sb-ext-add-implementation-package.texinfo
|
||||
@include fun-sb-ext-remove-implementation-package.texinfo
|
||||
@include macro-sb-ext-without-package-locks.texinfo
|
||||
@include macro-sb-ext-with-unlocked-packages.texinfo
|
||||
|
||||
@defmac @cl{defpackage} name [[option]]* @result{} package
|
||||
|
||||
Options are extended to include the following:
|
||||
@end example
|
||||
|
||||
@itemize
|
||||
@item
|
||||
@code{:lock} @var{boolean}
|
||||
@item Binding or altering its value lexically or dynamically, or
|
||||
establishing it as a symbol-macro.
|
||||
|
||||
If the argument to @code{:lock} is @code{t}, the package is initially
|
||||
locked. If @code{:lock} is not provided it defaults to @code{nil}.
|
||||
Exceptions:
|
||||
|
||||
@item
|
||||
@code{:implement} @var{package-designator}*
|
||||
@itemize
|
||||
@item If the symbol is not defined as a constant, global
|
||||
symbol-macro or a global dynamic variable, it may be lexically
|
||||
bound or established as a local symbol macro.
|
||||
|
||||
The package is added as an implementation package to the packages
|
||||
named. If @code{:implement} is not provided, it defaults to the
|
||||
package itself.
|
||||
@item If the symbol is defined as a global dynamic variable, it may
|
||||
be assigned or bound.
|
||||
@end itemize
|
||||
|
||||
@item Defining, undefining, or binding it, or its setf name as a
|
||||
function.
|
||||
|
||||
Exceptions:
|
||||
|
||||
@itemize
|
||||
@item If the symbol is not defined as a function, macro, or special
|
||||
operator it and its setf name may be lexically bound as a
|
||||
function.
|
||||
@end itemize
|
||||
|
||||
@item Defining, undefining, or binding it as a macro or compiler macro.
|
||||
|
||||
Exceptions:
|
||||
|
||||
@itemize
|
||||
@item If the symbol is not defined as a function, macro, or special
|
||||
operator it may be lexically bound as a macro.
|
||||
@end itemize
|
||||
|
||||
@item Defining it as a type specifier or structure.
|
||||
|
||||
@item Defining it as a declaration with a declaration proclamation.
|
||||
|
||||
@item Declaring or proclaiming it special.
|
||||
|
||||
@item Declaring or proclaiming its type or ftype.
|
||||
|
||||
Exceptions:
|
||||
|
||||
@itemize
|
||||
@item If the symbol may be lexically bound, the type of that binding
|
||||
may be declared.
|
||||
|
||||
@item If the symbol may be lexically bound as a function, the ftype
|
||||
of that binding may be declared.
|
||||
@end itemize
|
||||
|
||||
@item Defining a setf expander for it.
|
||||
|
||||
@item Defining it as a method combination type.
|
||||
|
||||
@item Using it as the @code{class-name} argument to (@code{setf} @code{find-class}).
|
||||
|
||||
@item Defining it as a hash table test using @code{sb-ext:define-hash-table-test}.
|
||||
@end itemize
|
||||
|
||||
@node package lock dictionary
|
||||
@section Package Lock Dictionary
|
||||
|
||||
@itemize
|
||||
@item [@strong{declaration}] @code{sb-ext:disable-package-locks}
|
||||
|
||||
Syntax: @code{(sb-ext:disable-package-locks &rest symbols)}
|
||||
|
||||
Disables package locks affecting the named symbols during
|
||||
compilation in the lexical scope of the declaration. Disabling
|
||||
locks on symbols whose home package is unlocked, or disabling an
|
||||
already disabled lock, has no effect.
|
||||
|
||||
@item [@strong{declaration}] @code{sb-ext:enable-package-locks}
|
||||
|
||||
Syntax: @code{(sb-ext:enable-package-locks &rest symbols)}
|
||||
|
||||
Re-enables package locks affecting the named symbols during
|
||||
compilation in the lexical scope of the declaration. Enabling
|
||||
locks that were not first disabled with
|
||||
@code{sb-ext:disable-package-locks} declaration, or enabling locks that
|
||||
are already enabled has no effect.
|
||||
@end itemize
|
||||
|
||||
@anchor{Condition sb-ext package-lock-violation}
|
||||
@ttindex @sortas{package-lock-violation sb-ext} package-lock-violation [sb-ext]
|
||||
@deffn{Condition} sb-ext:package-lock-violation
|
||||
Subtype of @code{cl:package-error}. A subtype of this error is signalled
|
||||
when a package-lock is violated.
|
||||
@end deffn
|
||||
@anchor{Condition sb-ext package-locked-error}
|
||||
@ttindex @sortas{package-locked-error sb-ext} package-locked-error [sb-ext]
|
||||
@deffn{Condition} sb-ext:package-locked-error
|
||||
Subtype of @code{sb-ext:package-lock-violation}. An error of this type is
|
||||
signalled when an operation on a package violates a package lock.
|
||||
@end deffn
|
||||
@anchor{Condition sb-ext symbol-package-locked-error}
|
||||
@ttindex @sortas{symbol-package-locked-error sb-ext} symbol-package-locked-error [sb-ext]
|
||||
@deffn{Condition} sb-ext:symbol-package-locked-error
|
||||
Subtype of @code{sb-ext:package-lock-violation}. An error of this type is
|
||||
signalled when an operation on a symbol violates a package lock. The
|
||||
symbol that caused the violation is accessed by the function
|
||||
@code{sb-ext:package-locked-error-symbol}.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext package-locked-error-symbol}
|
||||
@ffindex @sortas{package-locked-error-symbol sb-ext} package-locked-error-symbol [sb-ext]
|
||||
@deffn{Function} sb-ext:package-locked-error-symbol condition
|
||||
Return the symbol that caused the @code{symbol-package-locked-error}
|
||||
condition.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext package-locked-p}
|
||||
@ffindex @sortas{package-locked-p sb-ext} package-locked-p [sb-ext]
|
||||
@deffn{Function} sb-ext:package-locked-p package
|
||||
Returns @code{t} when @code{package} is locked, @code{nil} otherwise. Signals an error
|
||||
if @code{package} doesn't designate a valid package.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext lock-package}
|
||||
@ffindex @sortas{lock-package sb-ext} lock-package [sb-ext]
|
||||
@deffn{Function} sb-ext:lock-package package
|
||||
Locks @code{package} and returns @code{t}. Has no effect if @code{package} was already
|
||||
locked. Signals an error if @code{package} is not a valid package designator
|
||||
@end deffn
|
||||
@anchor{Function sb-ext unlock-package}
|
||||
@ffindex @sortas{unlock-package sb-ext} unlock-package [sb-ext]
|
||||
@deffn{Function} sb-ext:unlock-package package
|
||||
Unlocks @code{package} and returns @code{t}. Has no effect if @code{package} was already
|
||||
unlocked. Signals an error if @code{package} is not a valid package designator.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext package-implemented-by-list}
|
||||
@ffindex @sortas{package-implemented-by-list sb-ext} package-implemented-by-list [sb-ext]
|
||||
@deffn{Function} sb-ext:package-implemented-by-list package
|
||||
Returns a list containing the implementation packages of
|
||||
@code{package}. Signals an error if @code{package} is not a valid package designator.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext package-implements-list}
|
||||
@ffindex @sortas{package-implements-list sb-ext} package-implements-list [sb-ext]
|
||||
@deffn{Function} sb-ext:package-implements-list package
|
||||
Returns the packages that @code{package} is an implementation package
|
||||
of. Signals an error if @code{package} is not a valid package designator.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext add-implementation-package}
|
||||
@ffindex @sortas{add-implementation-package sb-ext} add-implementation-package [sb-ext]
|
||||
@deffn{Function} sb-ext:add-implementation-package packages-to-add &optional package
|
||||
Adds @code{packages-to-add} as implementation packages of @code{package}. Signals
|
||||
an error if @code{package} or any of the @code{packages-to-add} is not a valid
|
||||
package designator.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext remove-implementation-package}
|
||||
@ffindex @sortas{remove-implementation-package sb-ext} remove-implementation-package [sb-ext]
|
||||
@deffn{Function} sb-ext:remove-implementation-package packages-to-remove &optional package
|
||||
Removes @code{packages-to-remove} from the implementation packages of
|
||||
@code{package}. Signals an error if @code{package} or any of the @code{packages-to-remove}
|
||||
is not a valid package designator.
|
||||
@end deffn
|
||||
@anchor{Macro sb-ext without-package-locks}
|
||||
@ffindex @sortas{without-package-locks sb-ext} without-package-locks [sb-ext]
|
||||
@deffn{Macro} sb-ext:without-package-locks &body body
|
||||
Ignores all runtime package lock violations during the execution of
|
||||
body. Body can begin with declarations.
|
||||
@end deffn
|
||||
@anchor{Macro sb-ext with-unlocked-packages}
|
||||
@ffindex @sortas{with-unlocked-packages sb-ext} with-unlocked-packages [sb-ext]
|
||||
@deffn{Macro} sb-ext:with-unlocked-packages (&rest packages) &body forms
|
||||
Unlocks @code{packages} for the dynamic scope of the body. Signals an
|
||||
error if any of @code{packages} is not a valid package designator.
|
||||
@end deffn
|
||||
The @code{defpackage} options are extended to include the following:
|
||||
|
||||
@itemize
|
||||
@item @code{:lock} @code{<boolean>} (defaults to @code{nil})
|
||||
|
||||
If the argument to @code{:lock} is @code{t}, the package is locked, else it is
|
||||
unlocked. Existing package are also affected.
|
||||
|
||||
@item @code{:implement} @code{<package-designator>*}
|
||||
|
||||
The package is added as an implementation package to the
|
||||
packages named. If @code{:implement} is not provided, it defaults to
|
||||
the package itself.
|
||||
@end itemize
|
||||
|
||||
Example:
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(defpackage "FOO" (:export "BAR") (:lock t) (:implement))
|
||||
(defpackage "FOO-INT" (:use "FOO") (:implement "FOO" "FOO-INT"))
|
||||
|
||||
|
|
@ -373,7 +389,8 @@ Example:
|
|||
(defpackage "FOO") (:export "BAR"))
|
||||
(lock-package "FOO")
|
||||
(remove-implementation-package "FOO" "FOO")
|
||||
|
||||
(defpackage "FOO-INT" (:use "BAR"))
|
||||
(add-implementation-package "FOO-INT" "FOO")
|
||||
@end lisp
|
||||
@end defmac
|
||||
@end example
|
||||
|
||||
|
|
|
|||
|
|
@ -1,174 +1,146 @@
|
|||
@node Pathnames
|
||||
@comment node-name, next, previous, up
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node pathnames
|
||||
@chapter Pathnames
|
||||
|
||||
@cindex Pathnames
|
||||
|
||||
@menu
|
||||
* Lisp Pathnames::
|
||||
* Native Filenames::
|
||||
* Lisp Pathnames: lisp pathnames.
|
||||
* Native Filenames: native filenames.
|
||||
@end menu
|
||||
|
||||
@node Lisp Pathnames
|
||||
@comment node-name, next, previous, up
|
||||
@node lisp pathnames
|
||||
@section Lisp Pathnames
|
||||
|
||||
There are many aspects of ANSI Common Lisp's pathname support which are
|
||||
implementation-defined and so need documentation.
|
||||
@menu
|
||||
* Home Directory Specifiers: home directory specifiers.
|
||||
* The SYS Logical Pathname Host: the sys logical pathname host.
|
||||
@end menu
|
||||
|
||||
@c FIXME: as a matter of ANSI conformance, we are required to document
|
||||
@c implementation-defined stuff, which for pathnames (chapter 19 of CLtS)
|
||||
@c includes:
|
||||
@c
|
||||
@c * Otherwise, the parsing of thing is implementation-defined.
|
||||
@c (PARSE-NAMESTRING)
|
||||
@c
|
||||
@c * If thing contains an explicit host name and no explicit device name,
|
||||
@c then it is implementation-defined whether parse-namestring will supply
|
||||
@c the standard default device for that host as the device component of
|
||||
@c the resulting pathname. (PARSE-NAMESTRING)
|
||||
@c
|
||||
@c * The specific nature of the search is implementation-defined.
|
||||
@c (LOAD-LOGICAL-PATHNAME-TRANSLATIONS)
|
||||
@c
|
||||
@c * Any additional elements are implementation-defined.
|
||||
@c (LOGICAL-PATHNAME-TRANSLATIONS)
|
||||
@c
|
||||
@c * The matching rules are implementation-defined but should be consistent
|
||||
@c with directory. (PATHNAME-MATCH-P)
|
||||
@c
|
||||
@c * Any such additional translations are implementation-defined.
|
||||
@c (TRANSLATE-LOGICAL-PATHNAMES)
|
||||
@c
|
||||
@c * ...or an implementation-defined portion of a component...
|
||||
@c (TRANSLATE-PATHNAME)
|
||||
@c
|
||||
@c * The portion of source that is copied into the resulting pathname is
|
||||
@c implementation-defined. (TRANSLATE-PATHNAME)
|
||||
@c
|
||||
@c * During the copying of a portion of source into the resulting
|
||||
@c pathname, additional implementation-defined translations of case or
|
||||
@c file naming conventions might occur. (TRANSLATE-PATHNAME)
|
||||
@c
|
||||
@c * In general, the syntax of namestrings involves the use of
|
||||
@c implementation-defined conventions. (19.1.1)
|
||||
@c
|
||||
@c * The nature of the mapping between structure imposed by pathnames and
|
||||
@c the structure, if any, that is used by the underlying file system is
|
||||
@c implementation-defined. (19.1.2)
|
||||
@c
|
||||
@c * The mapping of the pathname components into the concepts peculiar to
|
||||
@c each file system is implementation-defined. (19.1.2)
|
||||
@c
|
||||
@c * Whether separator characters are permitted as part of a string in a
|
||||
@c pathname component is implementation-defined; (19.2.2.1.1)
|
||||
@c
|
||||
@c * Whether a value of :unspecific is permitted for any component on any
|
||||
@c given file system accessible to the implementation is
|
||||
@c implementation-defined. (19.2.2.2.3)
|
||||
@c
|
||||
@c * Other symbols and integers have implementation-defined meaning.
|
||||
@c (19.2.2.4.6)
|
||||
There are many aspects of ANSI Common Lisp's pathname support
|
||||
which are implementation-defined and so need documentation.
|
||||
|
||||
@node home directory specifiers
|
||||
@subsection Home Directory Specifiers
|
||||
|
||||
SBCL accepts the keyword @code{:home} and a list of the form
|
||||
@code{(:home "username")} as a directory component immediately
|
||||
@code{(:home} @code{"username")} as a directory component immediately
|
||||
following @code{:absolute}.
|
||||
|
||||
@code{:home} is represented in namestrings by @code{~/} and
|
||||
@code{(:home "username"} by @code{~username/} at the start of the
|
||||
namestring. Tilde-characters elsewhere in namestrings represent
|
||||
themselves.
|
||||
@code{:home} is represented in namestrings by @code{~/} and @code{(:home}
|
||||
@code{"username")} by @code{~username/} at the start of the namestring.
|
||||
Tilde-characters elsewhere in namestrings represent themselves.
|
||||
|
||||
Home directory specifiers are resolved to home directory of the
|
||||
current or specified user by @code{native-namestring}, which is used
|
||||
by the implementation to translate pathnames before passing them on to
|
||||
operating system specific routines.
|
||||
current or specified user by @code{sb-ext:native-namestring}, which is used
|
||||
by the implementation to translate pathnames before passing them on
|
||||
to operating system specific routines.
|
||||
|
||||
Using @code{(:home "user")} form on Windows signals an error.
|
||||
Using @code{(:home} @code{"user")} form on Windows signals an error.
|
||||
|
||||
@node the sys logical pathname host
|
||||
@subsection The SYS Logical Pathname Host
|
||||
|
||||
@cindex Logical pathnames
|
||||
@cindex Pathnames, logical
|
||||
@findex @cl{logical-pathname-translations}
|
||||
@findex @setf{@cl{logical-pathname-translations}}
|
||||
|
||||
@c * The existence and meaning of SYS: logical pathnames is
|
||||
@c implementation-defined. (19.3.1.1.1)
|
||||
|
||||
The logical pathname host named by @code{"SYS"} exists in SBCL. Its
|
||||
@code{logical-pathname-translations} may be set by the site or the user
|
||||
The logical pathname host named by @code{"SYS"} exists in SBCL.
|
||||
Its @code{logical-pathname-translations} may be set by the site or the user
|
||||
applicable to point to the locations of the system's sources; in
|
||||
particular, the core system's source files match the logical pathname
|
||||
@code{"SYS:SRC;**;*.*.*"}, and the contributed modules' source files
|
||||
match @code{"SYS:CONTRIB;**;*.*.*"}.
|
||||
particular, the core system's source files match the logical
|
||||
pathname @code{"SYS:SRC;**;*.*.*"}, and the contributed modules' source
|
||||
files match @code{"SYS:CONTRIB;**;*.*.*"}.
|
||||
|
||||
@include fun-sb-ext-set-sbcl-source-location.texinfo
|
||||
|
||||
@node Native Filenames
|
||||
@comment node-name, next, previous, up
|
||||
@anchor{Function sb-ext set-sbcl-source-location}
|
||||
@ffindex @sortas{set-sbcl-source-location sb-ext} set-sbcl-source-location [sb-ext]
|
||||
@deffn{Function} sb-ext:set-sbcl-source-location pathname
|
||||
Initialize the @code{SYS} logical host based on @code{pathname}, which should
|
||||
be the top-level directory of the SBCL sources. This will replace any
|
||||
existing translations for @code{"SYS:SRC;"}, @code{"SYS:CONTRIB;"}, and
|
||||
@code{"SYS:OUTPUT;"}. Other @code{"SYS:"} translations are preserved.
|
||||
@end deffn
|
||||
@node native filenames
|
||||
@section Native Filenames
|
||||
|
||||
In some circumstances, what is wanted is a Lisp pathname object which
|
||||
corresponds to a string produced by the Operating System. In this case,
|
||||
some of the default parsing rules are inappropriate: most filesystems do
|
||||
not have a native understanding of wild pathnames; such functionality is
|
||||
often provided by shells above the OS, often in mutually-incompatible
|
||||
ways.
|
||||
corresponds to a string produced by the Operating System. In this
|
||||
case, some of the default parsing rules are inappropriate: most
|
||||
filesystems do not have a native understanding of wild pathnames;
|
||||
such functionality is often provided by shells above the OS, often
|
||||
in mutually-incompatible ways.
|
||||
|
||||
To allow the user to deal with this, the following functions are
|
||||
provided: @code{parse-native-namestring} and @code{native-pathname}
|
||||
provided: @code{sb-ext:parse-native-namestring} and @code{sb-ext:native-pathname}
|
||||
return the closest equivalent Lisp pathname to a given string
|
||||
(appropriate for the Operating System), while @code{native-namestring}
|
||||
converts a non-wild pathname designator to the equivalent native
|
||||
namestring, if possible. Some Lisp pathname concepts (such as the
|
||||
@code{:back} directory component) have no direct equivalents in most
|
||||
Operating Systems; the behaviour of @code{native-namestring} is
|
||||
unspecified if an inappropriate pathname designator is passed to it.
|
||||
Additionally, note that conversion from pathname to native filename
|
||||
and back to pathname should not be expected to preserve equivalence
|
||||
under @code{equal}.
|
||||
|
||||
@include fun-sb-ext-parse-native-namestring.texinfo
|
||||
@include fun-sb-ext-native-pathname.texinfo
|
||||
@include fun-sb-ext-native-namestring.texinfo
|
||||
(appropriate for the Operating System), while
|
||||
@code{sb-ext:native-namestring} converts a non-wild pathname designator to
|
||||
the equivalent native namestring, if possible. Some Lisp pathname
|
||||
concepts (such as the @code{:back} directory component) have no direct
|
||||
equivalents in most Operating Systems; the behaviour of
|
||||
@code{sb-ext:native-namestring} is unspecified if an inappropriate pathname
|
||||
designator is passed to it. Additionally, note that conversion from
|
||||
pathname to native filename and back to pathname should not be
|
||||
expected to preserve equivalence under @code{equal}.
|
||||
|
||||
@anchor{Function sb-ext parse-native-namestring}
|
||||
@ffindex @sortas{parse-native-namestring sb-ext} parse-native-namestring [sb-ext]
|
||||
@deffn{Function} sb-ext:parse-native-namestring thing &optional host defaults &key start end junk-allowed as-directory
|
||||
Convert @code{thing} into a pathname, using the native conventions
|
||||
appropriate for the pathname host @code{host}, or if not specified the
|
||||
host of @code{defaults}. If @code{thing} is a string, the parse is bounded by
|
||||
@code{start} and @code{end}, and error behaviour is controlled by @code{junk-allowed},
|
||||
as with @code{parse-namestring}. For file systems whose native
|
||||
conventions allow directories to be indicated as files, if
|
||||
@code{as-directory} is true, return a pathname denoting @code{thing} as a
|
||||
directory.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext native-pathname}
|
||||
@ffindex @sortas{native-pathname sb-ext} native-pathname [sb-ext]
|
||||
@deffn{Function} sb-ext:native-pathname pathspec
|
||||
Convert @code{pathspec} (a pathname designator) into a pathname, assuming
|
||||
the operating system native pathname conventions.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext native-namestring}
|
||||
@ffindex @sortas{native-namestring sb-ext} native-namestring [sb-ext]
|
||||
@deffn{Function} sb-ext:native-namestring pathname &key as-file
|
||||
Construct the full native (name)string form of @code{pathname}. For
|
||||
file systems whose native conventions allow directories to be
|
||||
indicated as files, if @code{as-file} is true and the name, type, and
|
||||
version components of @code{pathname} are all @code{nil} or @code{:unspecific},
|
||||
construct a string that names the directory according to the file
|
||||
system's syntax for files.
|
||||
@end deffn
|
||||
Because some file systems permit the names of directories to be
|
||||
expressed in multiple ways, it is occasionally necessary to parse a
|
||||
native file name ``as a directory name'' or to produce a native file
|
||||
name that names a directory ``as a file''. For these cases,
|
||||
@code{parse-native-namestring} accepts the keyword argument
|
||||
@code{as-directory} to force a filename to parse as a directory, and
|
||||
@code{native-namestring} accepts the keyword argument @code{as-file}
|
||||
native file name as a directory name or to produce a native file
|
||||
name that names a directory as a file. For these cases,
|
||||
PARSE-NATIVE-NAMESTRING accepts the keyword argument
|
||||
@code{:as-directory} to force a filename to parse as a directory, and
|
||||
@code{sb-ext:native-namestring} accepts the keyword argument @code{:as-file}
|
||||
to force a pathname to unparse as a file. For example,
|
||||
|
||||
@lisp
|
||||
@example
|
||||
; On Unix, the directory "/tmp/" can be denoted by "/tmp/" or "/tmp".
|
||||
; Under the default rules for native filenames, these parse and
|
||||
; unparse differently.
|
||||
(defvar *p*)
|
||||
(setf *p* (parse-native-namestring "/tmp/")) @result{} #P"/tmp/"
|
||||
(pathname-name *p*) @result{} NIL
|
||||
(pathname-directory *p*) @result{} (:ABSOLUTE "tmp")
|
||||
(native-namestring *p*) @result{} "/tmp/"
|
||||
(setf *p* (parse-native-namestring "/tmp/")) => #P"/tmp/"
|
||||
(pathname-name *p*) => NIL
|
||||
(pathname-directory *p*) => (:ABSOLUTE "tmp")
|
||||
(native-namestring *p*) => "/tmp/"
|
||||
|
||||
(setf *p* (parse-native-namestring "/tmp")) @result{} #P"/tmp"
|
||||
(pathname-name *p*) @result{} "tmp"
|
||||
(pathname-directory *p*) @result{} (:ABSOLUTE)
|
||||
(native-namestring *p*) @result{} "/tmp"
|
||||
(setf *p* (parse-native-namestring "/tmp")) => #P"/tmp"
|
||||
(pathname-name *p*) => "tmp"
|
||||
(pathname-directory *p*) => (:ABSOLUTE)
|
||||
(native-namestring *p*) => "/tmp"
|
||||
|
||||
; A non-NIL AS-DIRECTORY argument to PARSE-NATIVE-NAMESTRING forces
|
||||
; both the second string to parse the way the first does.
|
||||
(setf *p* (parse-native-namestring "/tmp"
|
||||
nil *default-pathname-defaults*
|
||||
:as-directory t)) @result{} #P"/tmp/"
|
||||
(pathname-name *p*) @result{} NIL
|
||||
(pathname-directory *p*) @result{} (:ABSOLUTE "tmp")
|
||||
:as-directory t)) => #P"/tmp/"
|
||||
(pathname-name *p*) => NIL
|
||||
(pathname-directory *p*) => (:ABSOLUTE "tmp")
|
||||
|
||||
; A non-NIL AS-FILE argument to NATIVE-NAMESTRING forces the pathname
|
||||
; parsed from the first string to unparse as the second string.
|
||||
(setf *p* (parse-native-namestring "/tmp/")) @result{} #P"/tmp/"
|
||||
(native-namestring *p* :as-file t) @result{} "/tmp"
|
||||
@end lisp
|
||||
(setf *p* (parse-native-namestring "/tmp/")) => #P"/tmp/"
|
||||
(native-namestring *p* :as-file t) => "/tmp"
|
||||
@end example
|
||||
|
||||
|
|
|
|||
|
|
@ -1,37 +1,67 @@
|
|||
@node Profiling
|
||||
@comment node-name, next, previous, up
|
||||
@chapter Profiling
|
||||
@cindex Profiling
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
SBCL includes both a deterministic profiler, that can collect statistics
|
||||
on individual functions, and a more ``modern'' statistical profiler.
|
||||
@node profiling
|
||||
@chapter Profiling
|
||||
|
||||
@menu
|
||||
* Deterministic Profiler: deterministic profiler.
|
||||
* Statistical Profiler: statistical profiler.
|
||||
@end menu
|
||||
|
||||
SBCL includes both a deterministic profiler, that can collect
|
||||
statistics on individual functions, and a more "modern",
|
||||
statistical profiler.
|
||||
|
||||
Inlined functions do not appear in the results reported by either.
|
||||
|
||||
@menu
|
||||
* Deterministic Profiler::
|
||||
* Statistical Profiler::
|
||||
@end menu
|
||||
|
||||
@node Deterministic Profiler
|
||||
@comment node-name, next, previous, up
|
||||
@node deterministic profiler
|
||||
@section Deterministic Profiler
|
||||
@cindex Profiling, deterministic
|
||||
|
||||
The package @code{sb-profile} provides a classic, per-function-call
|
||||
profiler.
|
||||
|
||||
@quotation note
|
||||
When profiling code executed by multiple threads in parallel, the
|
||||
consing attributed to each function is inaccurate.
|
||||
@quotation
|
||||
@strong{Warning}: When profiling code executed by multiple threads in
|
||||
parallel, the consing attributed to each function is inaccurate.
|
||||
@end quotation
|
||||
|
||||
@include macro-sb-profile-profile.texinfo
|
||||
@include macro-sb-profile-unprofile.texinfo
|
||||
@include fun-sb-profile-report.texinfo
|
||||
@include fun-sb-profile-reset.texinfo
|
||||
@anchor{Macro sb-profile profile}
|
||||
@ffindex @sortas{profile sb-profile} profile [sb-profile]
|
||||
@deffn{Macro} sb-profile:profile &rest names
|
||||
If no names are supplied, return the list of profiled functions.
|
||||
|
||||
@node Statistical Profiler
|
||||
@comment node-name, next, previous, up
|
||||
@section Statistical Profiler
|
||||
@include sb-sprof/sb-sprof.texinfo
|
||||
If names are supplied, wrap profiling code around the named functions.
|
||||
As in @code{trace}, the names are not evaluated. A symbol names a function.
|
||||
A string names all the functions named by symbols in the named
|
||||
package. If a function is already profiled, then unprofile and
|
||||
reprofile (useful to notice function redefinition.) If a name is
|
||||
undefined, then we give a warning and ignore it. See also
|
||||
@code{unprofile}, @code{report} and @code{reset}.
|
||||
@end deffn
|
||||
@anchor{Macro sb-profile unprofile}
|
||||
@ffindex @sortas{unprofile sb-profile} unprofile [sb-profile]
|
||||
@deffn{Macro} sb-profile:unprofile &rest names
|
||||
Unwrap any profiling code around the named functions, or if no names
|
||||
are given, unprofile all profiled functions. A symbol names
|
||||
a function. A string names all the functions named by symbols in the
|
||||
named package. @code{names} defaults to the list of names of all currently
|
||||
profiled functions.
|
||||
@end deffn
|
||||
@anchor{Function sb-profile report}
|
||||
@ffindex @sortas{report sb-profile} report [sb-profile]
|
||||
@deffn{Function} sb-profile:report &key limit print-no-call-list
|
||||
Report results from profiling. The results are approximately
|
||||
adjusted for profiling overhead. The compensation may be rather
|
||||
inaccurate when bignums are involved in runtime calculation, as in a
|
||||
very-long-running Lisp process.
|
||||
|
||||
If @code{limit} is set to an integer, only the top @code{limit} results are
|
||||
reported. If @code{print-no-call-list} is @code{t} (the default) then a list of
|
||||
uncalled profiled functions are listed.
|
||||
@end deffn
|
||||
@anchor{Function sb-profile reset}
|
||||
@ffindex @sortas{reset sb-profile} reset [sb-profile]
|
||||
@deffn{Function} sb-profile:reset
|
||||
Reset the counters for all profiled functions.
|
||||
@end deffn
|
||||
@include ../../contrib/sb-sprof/sb-sprof.texinfo
|
||||
|
|
|
|||
|
|
@ -1,35 +1,34 @@
|
|||
@node Starting and Stopping
|
||||
@comment node-name, next, previous, up
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node starting and stopping
|
||||
@chapter Starting and Stopping
|
||||
|
||||
@menu
|
||||
* Starting SBCL::
|
||||
* Stopping SBCL::
|
||||
* Command Line Options::
|
||||
* Initialization Files::
|
||||
* Initialization and Exit Hooks::
|
||||
* Starting SBCL: starting sbcl.
|
||||
* Stopping SBCL: stopping sbcl.
|
||||
* Command Line Options: command line options.
|
||||
* Initialization Files: initialization files.
|
||||
* Initialization and Exit Hooks: initialization and exit hooks.
|
||||
@end menu
|
||||
|
||||
@node Starting SBCL
|
||||
@comment node-name, next, previous, up
|
||||
@node starting sbcl
|
||||
@section Starting SBCL
|
||||
|
||||
@menu
|
||||
* Running from Shell::
|
||||
* Running from Emacs::
|
||||
* Shebang Scripts::
|
||||
* Running from Shell: running from shell.
|
||||
* Running from Emacs: running from emacs.
|
||||
* Shebang Scripts: shebang scripts.
|
||||
@end menu
|
||||
|
||||
@node Running from Shell
|
||||
@comment node-name, next, previous, up
|
||||
@subsection From Shell to Lisp
|
||||
@node running from shell
|
||||
@subsection Running from Shell
|
||||
|
||||
To run SBCL, type @command{sbcl} at the command line.
|
||||
To run SBCL, type @code{sbcl} at the command line.
|
||||
|
||||
You should end up in the toplevel @dfn{REPL} (read-eval-print loop),
|
||||
You should end up in the toplevel @emph{REPL} (read-eval-print loop),
|
||||
where you can interact with SBCL by typing expressions.
|
||||
|
||||
@smallexample
|
||||
@example
|
||||
$ sbcl
|
||||
This is SBCL 0.8.13.60, an implementation of ANSI Common Lisp.
|
||||
More information about SBCL is available at <http://www.sbcl.org/>.
|
||||
|
|
@ -42,125 +41,310 @@ distribution for more information.
|
|||
4
|
||||
* (exit)
|
||||
$
|
||||
@end smallexample
|
||||
@end example
|
||||
|
||||
See also @ref{Command Line Options} and @ref{Stopping SBCL}.
|
||||
Also see @ref{command line options} and @ref{stopping sbcl}.
|
||||
|
||||
@node Running from Emacs
|
||||
@comment node-name, next, previous, up
|
||||
@node running from emacs
|
||||
@subsection Running from Emacs
|
||||
|
||||
To run SBCL as an @code{inferior-lisp} from Emacs, in your
|
||||
@file{.emacs} do something like:
|
||||
To run SBCL as an @code{inferior-lisp} from Emacs, in your @code{.emacs} do
|
||||
something like:
|
||||
|
||||
@lisp
|
||||
@example
|
||||
;;; The SBCL binary and command-line arguments
|
||||
(setq inferior-lisp-program "/usr/local/bin/sbcl --noinform")
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
For more information on using SBCL with Emacs, see @ref{Editor
|
||||
Integration}.
|
||||
For more information on using SBCL with Emacs, see
|
||||
@ref{editor integration}.
|
||||
|
||||
|
||||
@node Shebang Scripts
|
||||
@comment node-name, next, previous, up
|
||||
@node shebang scripts
|
||||
@subsection Shebang Scripts
|
||||
@vindex @sbext{@earmuffs{posix-argv}}
|
||||
|
||||
Standard Unix tools that are interpreters follow a common command line
|
||||
protocol that is necessary to work with ``shebang scripts''. SBCL supports
|
||||
this via the @code{--script} command line option @pxref{Command Line Options}.
|
||||
protocol that is necessary to work with "shebang scripts". SBCL
|
||||
supports this via the @code{--script} command line option (see
|
||||
@ref{command line options}).
|
||||
|
||||
Example file (@file{hello.lisp}):
|
||||
Example file (@code{hello.lisp}):
|
||||
|
||||
@lisp
|
||||
@example
|
||||
#!/usr/local/bin/sbcl --script
|
||||
(write-line "Hello, World!")
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
Usage from the command line:
|
||||
|
||||
@smallexample
|
||||
@example
|
||||
$ ./hello.lisp
|
||||
Hello, World!
|
||||
@end smallexample
|
||||
@end example
|
||||
|
||||
Note that SBCL skips the shebang line when it reads the file:
|
||||
|
||||
@smallexample
|
||||
@example
|
||||
$ sbcl --script hello.lisp
|
||||
Hello, World!
|
||||
@end smallexample
|
||||
@end example
|
||||
|
||||
@node Stopping SBCL
|
||||
@comment node-name, next, previous, up
|
||||
@node stopping sbcl
|
||||
@section Stopping SBCL
|
||||
|
||||
@menu
|
||||
* Exit::
|
||||
* End of File::
|
||||
* Saving a Core Image::
|
||||
* Exit on Errors::
|
||||
* Exit: exit.
|
||||
* End of File: end of file.
|
||||
* Saving a Core Image: saving a core image.
|
||||
* Exit on Errors: exit on errors.
|
||||
@end menu
|
||||
|
||||
@node Exit
|
||||
@comment node-name, next, previous, up
|
||||
@node exit
|
||||
@subsection Exit
|
||||
|
||||
SBCL can be stopped at any time by calling @code{sb-ext:exit},
|
||||
optionally returning a specified numeric value to the calling process.
|
||||
See @ref{Threading} for information about terminating individual threads.
|
||||
optionally returning a specified numeric value to the calling
|
||||
process. See @ref{threading} for information about terminating individual
|
||||
threads.
|
||||
|
||||
@include fun-sb-ext-exit.texinfo
|
||||
@anchor{Function sb-ext exit}
|
||||
@ffindex @sortas{exit sb-ext} exit [sb-ext]
|
||||
@deffn{Function} sb-ext:exit &key code abort timeout
|
||||
Terminates the process, causing SBCL to exit with @code{code}. @code{code}
|
||||
defaults to 0 when @code{abort} is false, and 1 when it is true.
|
||||
|
||||
@node End of File
|
||||
@comment node-name, next, previous, up
|
||||
When @code{abort} is false (the default), current thread is first unwound,
|
||||
@code{*exit-hooks*} are run, other threads are terminated, and standard
|
||||
output streams are flushed before SBCL calls @code{exit(3)} -- at which point
|
||||
@code{atexit(3)} functions will run. If multiple threads call @code{exit} with @code{abort}
|
||||
being false, the first one to call it will complete the protocol.
|
||||
|
||||
When @code{abort} is true, SBCL exits immediately by calling @code{_exit(2)}
|
||||
without unwinding stack, or calling exit hooks. Note that @code{_exit(2)}
|
||||
does not call @code{atexit(3)} functions unlike @code{exit(3)}.
|
||||
|
||||
Recursive calls to @code{exit} cause @code{exit} to behave as if @code{abort} was true.
|
||||
|
||||
@code{timeout} controls waiting for other threads to terminate when @code{abort} is
|
||||
@code{nil}. Once current thread has been unwound and @code{*exit-hooks*} have been
|
||||
run, spawning new threads is prevented and all other threads are
|
||||
terminated by calling @code{sb-thread:terminate-thread} on them. The system
|
||||
then waits for them to finish using @code{sb-thread:join-thread}, waiting at
|
||||
most a total @code{timeout} seconds for all threads to join. Those threads
|
||||
that do not finish in time are simply ignored while the exit protocol
|
||||
continues. @code{timeout} defaults to @code{*exit-timeout*}, which in turn defaults
|
||||
to 60. @code{timeout} @code{nil} means to wait indefinitely.
|
||||
|
||||
Note that @code{timeout} applies only to @code{sb-thread:join-thread}, not
|
||||
@code{*exit-hooks*}. Since @code{sb-thread:terminate-thread} is asynchronous,
|
||||
getting multithreaded application termination with complex cleanups
|
||||
right using it can be tricky. To perform an orderly synchronous
|
||||
shutdown use an exit hook instead of relying on implicit thread
|
||||
termination.
|
||||
|
||||
Consequences are unspecified if serious conditions occur during @code{exit}
|
||||
excepting errors from @code{*exit-hooks*}, which cause warnings and stop
|
||||
execution of the hook that signaled, but otherwise allow the exit
|
||||
process to continue normally.
|
||||
@end deffn
|
||||
@node end of file
|
||||
@subsection End of File
|
||||
|
||||
By default SBCL also exits on end of input, caused either by user
|
||||
pressing @kbd{Control-D} on an attached terminal, or end of input when
|
||||
pressing @code{Control-D} on an attached terminal, or end of input when
|
||||
using SBCL as part of a shell pipeline.
|
||||
|
||||
@node Saving a Core Image
|
||||
@comment node-name, next, previous, up
|
||||
@node saving a core image
|
||||
@subsection Saving a Core Image
|
||||
|
||||
SBCL has the ability to save its state as a file for later
|
||||
execution. This functionality is important for its bootstrapping
|
||||
process, and is also provided as an extension to the user.
|
||||
|
||||
@include fun-sb-ext-save-lisp-and-die.texinfo
|
||||
@include var-sb-ext-star-save-hooks-star.texinfo
|
||||
@anchor{Function sb-ext save-lisp-and-die}
|
||||
@ffindex @sortas{save-lisp-and-die sb-ext} save-lisp-and-die [sb-ext]
|
||||
@deffn{Function} sb-ext:save-lisp-and-die core-file-name &key toplevel executable save-runtime-options callable-exports purify root-structures environment-name compression
|
||||
Save a "core image", i.e. enough information to restart a Lisp
|
||||
process later in the same state, in the file of the specified name.
|
||||
Only global state is preserved: the stack is unwound in the process.
|
||||
|
||||
The following @code{&key} arguments are defined:
|
||||
|
||||
@itemize
|
||||
@item @code{:toplevel}
|
||||
|
||||
The function to run when the created core file is resumed. The
|
||||
default function handles command line toplevel option
|
||||
processing (see @ref{toplevel options}) and runs the top
|
||||
level read-eval-print loop. This function returning is equivalent
|
||||
to (@code{sb-ext:exit} @code{:code} 0) being called.
|
||||
|
||||
@code{toplevel} functions should always provide an @code{abort} restart:
|
||||
otherwise code they call will run without one.
|
||||
|
||||
@item @code{:executable}
|
||||
|
||||
If true, arrange to combine the SBCL runtime and the core image to
|
||||
create a standalone executable. If false (the default), the core
|
||||
image will not be executable on its own. Executable images always
|
||||
behave as if they were passed the @code{--noinform} runtime option.
|
||||
If @code{:executable} is @code{:elf-object}, then the resulting core will be
|
||||
wrapped in a .o which requires further linking. (EXPERIMENTAL)
|
||||
|
||||
@item @code{:save-runtime-options}
|
||||
|
||||
If true, values of runtime options @code{--dynamic-space-size} and
|
||||
@code{--control-stack-size} that were used to start SBCL are stored in
|
||||
the standalone executable, and restored when the executable is
|
||||
run. This also inhibits normal runtime option processing, causing
|
||||
all command line arguments to be passed to the toplevel. If
|
||||
@code{:accept-runtime-options} then @code{--dynamic-space-size} and
|
||||
@code{--control-stack-size} are still processed by the runtime.
|
||||
Meaningless if @code{:executable} is @code{nil}.
|
||||
|
||||
@item @code{:callable-exports}
|
||||
|
||||
This should be a list of symbols to be initialized to the
|
||||
appropriate alien callables on startup. All exported symbols
|
||||
should be present as global symbols in the symbol table of the
|
||||
runtime before the saved core is loaded. When this list is
|
||||
non-empty, the @code{:toplevel} argument cannot be supplied.
|
||||
|
||||
@item @code{:purify}
|
||||
|
||||
If true (the default), then some objects in the restarted core
|
||||
will be memory-mapped as read-only. Among those objects are
|
||||
numeric vectors that were determined to be compile-time constants,
|
||||
and any immutable values according to the language specification
|
||||
such as symbol names.
|
||||
|
||||
@item @code{:root-structures}
|
||||
|
||||
This should be a list of the main entry points in any newly loaded
|
||||
systems. This need not be supplied, but locality and/or @code{gc}
|
||||
performance may be better if they are. This has two different but
|
||||
related meanings: If @code{:purify} is true - and only for cheneygc - the
|
||||
root structures are those which anchor the set of objects moved
|
||||
into static space. On gencgc - and only on platforms supporting
|
||||
immobile code - these are the functions and/or function-names
|
||||
which commence a depth-first scan of code when reordering based on
|
||||
the statically observable call chain. The complete set of
|
||||
reachable objects is not affected per se. This argument is
|
||||
meaningless if neither enabling precondition holds.
|
||||
|
||||
@item @code{:environment-name}
|
||||
|
||||
This has no purpose; it is accepted only for legacy compatibility.
|
||||
|
||||
@item @code{:compression}
|
||||
|
||||
This is only meaningful if the runtime was built with the
|
||||
@code{:sb-core-compression} feature enabled. If @code{nil} (the default),
|
||||
saves to uncompressed core files. If @code{:sb-core-compression} was
|
||||
enabled at build-time, the argument may also be an integer from -7
|
||||
to 22, corresponding to zstd compression levels, or @code{t} (which is
|
||||
equivalent to the default compression level, 9).
|
||||
|
||||
@item @code{:application-type}
|
||||
|
||||
Present only on Windows and is meaningful only with @code{:executable} @code{t}.
|
||||
Specifies the subsystem of the executable, @code{:console} or @code{:gui}.
|
||||
The notable difference is that @code{:gui} doesn't automatically create
|
||||
a console window. The default is @code{:console}.
|
||||
@end itemize
|
||||
|
||||
The save/load process changes the values of some global variables:
|
||||
|
||||
@itemize
|
||||
@item @code{*standard-output*}, @code{*debug-io*}, etc
|
||||
|
||||
Everything related to open streams is necessarily changed, since
|
||||
the OS won't let us preserve a stream across save and load.
|
||||
|
||||
@item @code{*default-pathname-defaults*}
|
||||
|
||||
This is reinitialized to reflect the working directory where the
|
||||
saved core is loaded.
|
||||
@end itemize
|
||||
|
||||
@code{save-lisp-and-die} interacts with @code{sb-alien:load-shared-object}: see its
|
||||
documentation for details.
|
||||
|
||||
On threaded platforms only a single thread may remain running after
|
||||
@code{sb-ext:*save-hooks*} have run. Applications using multiple threads can
|
||||
be @code{save-lisp-and-die} friendly by registering a save-hook that quits
|
||||
any additional threads, and an init-hook that restarts them.
|
||||
|
||||
This implementation is not as polished and painless as you might like:
|
||||
|
||||
@itemize
|
||||
@item It corrupts the current Lisp image enough that the current process
|
||||
needs to be killed afterwards. This can be worked around by forking
|
||||
another process that saves the core.
|
||||
|
||||
@item There is absolutely no binary compatibility of core images between
|
||||
different runtime support programs. Even runtimes built from the
|
||||
same sources at different times are treated as incompatible for this
|
||||
purpose.
|
||||
@end itemize
|
||||
|
||||
This isn't because we like it this way, but just because there don't
|
||||
seem to be good quick fixes for either limitation and no one has been
|
||||
sufficiently motivated to do lengthy fixes.
|
||||
@end deffn
|
||||
@anchor{Variable sb-ext *save-hooks*}
|
||||
@vvindex @sortas{save-hooks* sb-ext} *save-hooks* [sb-ext]
|
||||
@deffn{Variable} sb-ext:*save-hooks*
|
||||
A list of function designators which are called in an unspecified
|
||||
order before creating a saved core image.
|
||||
|
||||
Unused by SBCL itself: reserved for user and applications.
|
||||
@end deffn
|
||||
In cases where the standard initialization files have already been loaded
|
||||
into the saved core, and alternative ones should be used (or none at all),
|
||||
SBCL allows customizing the initfile pathname computation.
|
||||
|
||||
@include var-sb-ext-star-sysinit-pathname-function-star.texinfo
|
||||
@include var-sb-ext-star-userinit-pathname-function-star.texinfo
|
||||
into the saved core, and alternative ones should be used (or none at
|
||||
all), SBCL allows customizing the initfile pathname computation.
|
||||
|
||||
@anchor{Variable sb-ext *sysinit-pathname-function*}
|
||||
@vvindex @sortas{sysinit-pathname-function* sb-ext} *sysinit-pathname-function* [sb-ext]
|
||||
@deffn{Variable} sb-ext:*sysinit-pathname-function*
|
||||
Designator for a function of zero arguments called to obtain a
|
||||
pathname designator for the default sysinit file, or @code{nil}. If the
|
||||
function returns @code{nil}, no sysinit file is used unless one has been
|
||||
specified on the command-line.
|
||||
@end deffn
|
||||
@anchor{Variable sb-ext *userinit-pathname-function*}
|
||||
@vvindex @sortas{userinit-pathname-function* sb-ext} *userinit-pathname-function* [sb-ext]
|
||||
@deffn{Variable} sb-ext:*userinit-pathname-function*
|
||||
Designator for a function of zero arguments called to obtain a
|
||||
pathname designator or a stream for the default userinit file, or @code{nil}.
|
||||
If the function returns @code{nil}, no userinit file is used unless one has
|
||||
been specified on the command-line.
|
||||
@end deffn
|
||||
To facilitate distribution of SBCL applications using external
|
||||
resources, the filesystem location of the SBCL core file being used is
|
||||
available from Lisp.
|
||||
resources, the filesystem location of the SBCL core file being used
|
||||
is available from Lisp.
|
||||
|
||||
@include var-sb-ext-star-core-pathname-star.texinfo
|
||||
|
||||
@node Exit on Errors
|
||||
@comment node-name, next, previous, up
|
||||
@anchor{Variable sb-ext *core-pathname*}
|
||||
@vvindex @sortas{core-pathname* sb-ext} *core-pathname* [sb-ext]
|
||||
@deffn{Variable} sb-ext:*core-pathname*
|
||||
The absolute pathname of the running SBCL core.
|
||||
@end deffn
|
||||
@node exit on errors
|
||||
@subsection Exit on Errors
|
||||
|
||||
SBCL can also be configured to exit if an unhandled error occurs,
|
||||
which is mainly useful for acting as part of a shell pipeline; doing
|
||||
so under most other circumstances would mean giving up large parts of
|
||||
the flexibility and robustness of Common Lisp. See @ref{Debugger Entry}.
|
||||
so under most other circumstances would mean giving up large parts
|
||||
of the flexibility and robustness of Common Lisp. See
|
||||
@ref{debugger entry} and the command line option @code{--disable-debugger} in
|
||||
@ref{runtime options}.
|
||||
|
||||
@node Command Line Options
|
||||
@comment node-name, next, previous, up
|
||||
@node command line options
|
||||
@section Command Line Options
|
||||
|
||||
@c FIXME: This is essentially cut-and-paste from the manpage
|
||||
@c What should probably be done is generate both this and the
|
||||
@c man-page from ``sbcl --help'' output.
|
||||
@menu
|
||||
* Runtime Options: runtime options.
|
||||
* Toplevel Options: toplevel options.
|
||||
@end menu
|
||||
|
||||
Command line options can be considered an advanced topic; for ordinary
|
||||
interactive use, no command line arguments should be necessary.
|
||||
|
|
@ -170,13 +354,19 @@ is helpful to understand that the SBCL system is implemented as two
|
|||
components, a low-level runtime environment written in C and a
|
||||
higher-level system written in Common Lisp itself. Some command line
|
||||
arguments are processed during the initialization of the low-level
|
||||
runtime environment, some command line arguments are processed during
|
||||
the initialization of the Common Lisp system, and any remaining
|
||||
command line arguments are passed on to user code.
|
||||
runtime environment, some command line arguments are processed
|
||||
during the initialization of the Common Lisp system, and any
|
||||
remaining command line arguments are made available to user code via
|
||||
@code{sb-ext:*posix-argv*}.
|
||||
|
||||
The full, unambiguous syntax for invoking SBCL at the command line is:
|
||||
The full, unambiguous syntax for invoking SBCL at the command line
|
||||
is:
|
||||
|
||||
@command{sbcl} @var{runtime-option}* @code{--end-runtime-options} @var{toplevel-option}* @code{--end-toplevel-options} @var{user-option}*
|
||||
@example
|
||||
sbcl <runtime-option>* --end-runtime-options \
|
||||
<toplevel-option>* --end-toplevel-options \
|
||||
<user-option>*
|
||||
@end example
|
||||
|
||||
For convenience, @code{--end-runtime-options} and
|
||||
@code{--end-toplevel-options} can be omitted, which can be convenient
|
||||
|
|
@ -185,210 +375,236 @@ no ambiguities are possible with the option values you are using.
|
|||
Omitting these elements is probably a bad idea for any batch file
|
||||
where any of the options are under user control, since it makes it
|
||||
impossible for SBCL to detect erroneous command line input, so that
|
||||
erroneous command line arguments will be passed on to the user program
|
||||
even if they was intended for the runtime system or the Lisp system.
|
||||
erroneous command line arguments will be passed on to the user
|
||||
program even if they was intended for the runtime system or the Lisp
|
||||
system.
|
||||
|
||||
@menu
|
||||
* Runtime Options::
|
||||
* Toplevel Options::
|
||||
@end menu
|
||||
|
||||
@node Runtime Options
|
||||
@comment node-name, next, previous, up
|
||||
@node runtime options
|
||||
@subsection Runtime Options
|
||||
|
||||
@table @code
|
||||
@itemize
|
||||
@item @code{--core <corefilename>}
|
||||
|
||||
@item --core @var{corefilename}
|
||||
Run the specified Lisp core file instead of the default. Note that if
|
||||
the Lisp core file is a user-created core file, it may run a
|
||||
nonstandard toplevel which does not recognize the standard toplevel
|
||||
options.
|
||||
Run the specified Lisp core file instead of the default. Note
|
||||
that if the Lisp core file is a user-created core file, it may
|
||||
run a nonstandard toplevel which does not recognize the standard
|
||||
toplevel options.
|
||||
|
||||
@item --dynamic-space-size @var{megabytes}
|
||||
Size of the dynamic space reserved on startup in megabytes. Default
|
||||
value is platform dependent.
|
||||
@item @code{--dynamic-space-size <megabytes>}
|
||||
|
||||
@item --control-stack-size @var{megabytes}
|
||||
Size of control stack reserved for each thread in megabytes. Default
|
||||
value is 2.
|
||||
Size of the dynamic space reserved on startup in megabytes.
|
||||
Default value is platform dependent.
|
||||
|
||||
@item --tls-limit @var{positive integer}
|
||||
Maximum number of thread-local symbols in threaded builds. Default
|
||||
value is 4096.
|
||||
@item @code{--control-stack-size <megabytes>}
|
||||
|
||||
@item --noinform
|
||||
Suppress the printing of any banner or other informational message at
|
||||
startup. This makes it easier to write Lisp programs which work
|
||||
cleanly in Unix pipelines. See also the @code{--noprint} and
|
||||
@code{--disable-debugger} options.
|
||||
Size of control stack reserved for each thread in megabytes.
|
||||
Default value is 2.
|
||||
|
||||
@item --disable-ldb
|
||||
@cindex ldb
|
||||
@cindex ldb, disabling
|
||||
@cindex disabling ldb
|
||||
Disable the low-level debugger. Only effective if SBCL is compiled
|
||||
with LDB.
|
||||
@item @code{--tls-limit <positive integer>}
|
||||
|
||||
@item --lose-on-corruption
|
||||
@cindex ldb
|
||||
There are some dangerous low-level errors (for instance, control stack
|
||||
exhausted, memory fault) that (or whose handlers) can corrupt the
|
||||
image. By default, SBCL prints a warning, then tries to continue and
|
||||
handle the error in Lisp, but this will not always work, and SBCL may
|
||||
malfunction or even hang. With this option, upon encountering such an
|
||||
error, SBCL will exit instead of invoking LDB (if present and
|
||||
enabled).
|
||||
Maximum number of thread-local symbols in threaded builds.
|
||||
Default value is 4096.
|
||||
|
||||
@item @code{--noinform}
|
||||
|
||||
Suppress the printing of any banner or other informational
|
||||
message at startup. This makes it easier to write Lisp programs
|
||||
which work cleanly in Unix pipelines. See also the @code{--noprint}
|
||||
and @code{--disable-debugger} options.
|
||||
|
||||
@item @code{--disable-ldb}
|
||||
|
||||
Disable the low-level debugger. Only effective if SBCL is
|
||||
compiled with @code{ldb}.
|
||||
|
||||
@item @code{--lose-on-corruption}
|
||||
|
||||
There are some dangerous low-level errors (for instance, control
|
||||
stack exhausted, memory fault) that (or whose handlers) can
|
||||
corrupt the image. By default, SBCL prints a warning, then tries
|
||||
to continue and handle the error in Lisp, but this will not
|
||||
always work, and SBCL may malfunction or even hang. With this
|
||||
option, upon encountering such an error, SBCL will exit instead
|
||||
of invoking @code{ldb} (if present and enabled).
|
||||
|
||||
@item @code{--script <filename>}
|
||||
|
||||
@item --script @var{filename}
|
||||
As a @emph{runtime} option, this is equivalent to @code{--noinform}
|
||||
@code{--disable-ldb} @code{--lose-on-corruption}
|
||||
@code{--end-runtime-options} @code{--script} @var{filename}. See the
|
||||
description of @code{--script} as a @emph{toplevel} option below. If
|
||||
there are no other command line arguments following @code{--script},
|
||||
the filename argument can be omitted.
|
||||
@code{--end-runtime-options} @code{--script} @code{<filename>}. See
|
||||
the description of @code{--script} as a @emph{toplevel} option below.
|
||||
If there are no other command line arguments following
|
||||
@code{--script}, the filename argument can be omitted.
|
||||
|
||||
@item @code{--merge-core-pages}
|
||||
|
||||
@item --merge-core-pages
|
||||
When platform support is present, provide hints to the operating system
|
||||
that identical pages may be shared between processes until they are
|
||||
written to. This can be useful to reduce the memory usage on systems
|
||||
with multiple SBCL processes started from similar but differently-named
|
||||
core files, or from compressed cores. Without platform support, do
|
||||
nothing. By default only compressed cores trigger hinting.
|
||||
When platform support is present, provide hints to the operating
|
||||
system that identical pages may be shared between processes
|
||||
until they are written to. This can be useful to reduce the
|
||||
memory usage on systems with multiple SBCL processes started
|
||||
from similar but differently-named core files, or from
|
||||
compressed cores. Without platform support, do nothing. By
|
||||
default only compressed cores trigger hinting.
|
||||
|
||||
@item --no-merge-core-pages
|
||||
Ensures that no sharing hint is provided to the operating system.
|
||||
@item @code{--no-merge-core-pages}
|
||||
|
||||
Ensures that no sharing hint is provided to the operating
|
||||
system.
|
||||
|
||||
@item @code{--help}
|
||||
|
||||
@item --help
|
||||
Print some basic information about SBCL, then exit.
|
||||
|
||||
@item --version
|
||||
@item @code{--version}
|
||||
|
||||
Print SBCL's version information, then exit.
|
||||
@end itemize
|
||||
|
||||
@end table
|
||||
In the future, runtime options may be added to control behaviour
|
||||
such as lazy allocation of memory.
|
||||
|
||||
In the future, runtime options may be added to control behaviour such
|
||||
as lazy allocation of memory.
|
||||
Runtime options, including any @code{--end-runtime-options} option, are
|
||||
stripped out of the command line before the Lisp toplevel logic gets
|
||||
a chance to see it.
|
||||
|
||||
Runtime options, including any @code{--end-runtime-options} option,
|
||||
are stripped out of the command line before the Lisp toplevel logic
|
||||
gets a chance to see it.
|
||||
|
||||
@node Toplevel Options
|
||||
@comment node-name, next, previous, up
|
||||
@node toplevel options
|
||||
@subsection Toplevel Options
|
||||
|
||||
@table @code
|
||||
The following options are processed and removed by the default
|
||||
toplevel (see @code{sb-ext:save-lisp-and-die}).
|
||||
|
||||
@item --sysinit @var{filename}
|
||||
Load filename instead of the default system initialization file
|
||||
(@pxref{Initialization Files}.)
|
||||
@itemize
|
||||
@item @code{--sysinit <filename>}
|
||||
|
||||
@item --no-sysinit
|
||||
Don't load a system-wide initialization file. If this option is given,
|
||||
the @code{--sysinit} option is ignored.
|
||||
Load @code{filename} instead of the default system initialization
|
||||
file (see @ref{initialization files}).
|
||||
|
||||
@item --userinit @var{filename}
|
||||
Load filename instead of the default user initialization file
|
||||
(@pxref{Initialization Files}.)
|
||||
@item @code{--no-sysinit}
|
||||
|
||||
Don't load a system-wide initialization file. If this option is
|
||||
given, the @code{--sysinit} option is ignored.
|
||||
|
||||
@item @code{--userinit <filename>}
|
||||
|
||||
Load @code{filename} instead of the default user initialization file
|
||||
(see @ref{initialization files}.)
|
||||
|
||||
@item @code{--no-userinit}
|
||||
|
||||
@item --no-userinit
|
||||
Don't load a user initialization file. If this option is given,
|
||||
the @code{--userinit} option is ignored.
|
||||
|
||||
@item --eval @var{command}
|
||||
@item @code{--eval <command>}
|
||||
|
||||
After executing any initialization file, but before starting the
|
||||
read-eval-print loop on standard input, read and evaluate the command
|
||||
given. More than one @code{--eval} option can be used, and all will be
|
||||
read and executed, in the order they appear on the command line.
|
||||
read-eval-print loop on standard input, read and evaluate
|
||||
@code{command}. More than one @code{--eval} option can be used, and all
|
||||
will be read and executed, in the order they appear on the
|
||||
command line.
|
||||
|
||||
@item --load @var{filename}
|
||||
This is equivalent to @code{--eval '(load "@var{filename}")'}. The
|
||||
special syntax is intended to reduce quoting headaches when invoking
|
||||
SBCL from shell scripts.
|
||||
@item @code{--load <filename>}
|
||||
|
||||
@item --noprint
|
||||
When ordinarily the toplevel "read-eval-print loop" would be executed,
|
||||
execute a "read-eval loop" instead, i.e. don't print a prompt and
|
||||
don't echo results. Combined with the @code{--noinform} runtime
|
||||
option, this makes it easier to write Lisp "scripts" which work
|
||||
cleanly in Unix pipelines.
|
||||
This is equivalent to @code{--eval '(load "<filename>")'}. The
|
||||
special syntax is intended to reduce quoting headaches when
|
||||
invoking SBCL from shell scripts.
|
||||
|
||||
@item @code{--noprint}
|
||||
|
||||
When ordinarily the toplevel "read-eval-print loop" would be
|
||||
executed, execute a "read-eval loop" instead, i.e. don't print
|
||||
a prompt and don't echo results. Combined with the @code{--noinform}
|
||||
runtime option, this makes it easier to write Lisp "scripts"
|
||||
which work cleanly in Unix pipelines.
|
||||
|
||||
@item @code{--disable-debugger}
|
||||
|
||||
@item --disable-debugger
|
||||
By default when SBCL encounters an error, it enters the builtin
|
||||
debugger, allowing interactive diagnosis and possible intercession.
|
||||
This option disables the debugger, causing errors to print a backtrace
|
||||
and exit with status 1 instead. When given, this option takes effect
|
||||
before loading of initialization files or processing @code{--eval} and
|
||||
@code{--load} options. See @code{sb-ext:disable-debugger} for details.
|
||||
@xref{Debugger Entry}.
|
||||
debugger, allowing interactive diagnosis and possible
|
||||
intercession. This option disables the debugger, causing errors
|
||||
to print a backtrace and exit with status 1 instead. When given,
|
||||
this option takes effect before loading of initialization files
|
||||
or processing @code{--eval} and @code{--load} options. See
|
||||
@code{sb-ext:disable-debugger} and @ref{debugger entry}.
|
||||
|
||||
@item --script @var{filename}
|
||||
Implies @code{--no-userinit} @code{--no-sysinit}
|
||||
@code{--disable-debugger} @code{--end-toplevel-options}.
|
||||
@item @code{--script <filename>}
|
||||
|
||||
Causes the system to load the specified file instead of entering the
|
||||
read-eval-print-loop, and exit afterwards. If the file begins with a
|
||||
shebang line, it is ignored.
|
||||
Implies @code{--no-userinit} @code{--no-sysinit} @code{--disable-debugger}
|
||||
@code{--end-toplevel-options}.
|
||||
|
||||
If there are no other command line arguments following, the filename
|
||||
can be omitted: this causes the script to be loaded from standard
|
||||
input instead. Shebang lines in standard input script are currently
|
||||
@emph{not} ignored.
|
||||
Causes the system to load the specified file instead of entering
|
||||
the read-eval-print-loop, and exit afterwards. If the file
|
||||
begins with a shebang line, it is ignored.
|
||||
|
||||
In either case, if there is an unhandled error (e.g. end of file, or a
|
||||
broken pipe) on either standard input, standard output, or standard
|
||||
error, the script silently exits with code 0. This allows e.g. safely
|
||||
piping output from SBCL to @code{head -n1} or similar.
|
||||
If there are no other command line arguments following, the
|
||||
filename can be omitted: this causes the script to be loaded
|
||||
from standard input instead. Shebang lines in standard input
|
||||
script are currently @emph{not} ignored.
|
||||
|
||||
In either case, if there is an unhandled error (e.g. end of
|
||||
file, or a broken pipe) on either standard input, standard
|
||||
output, or standard error, the script silently exits with code
|
||||
0. This allows e.g. safely piping output from SBCL to @code{head -n1}
|
||||
or similar.
|
||||
|
||||
Additionally, the option sets @code{*compile-verbose*} and
|
||||
@code{*load-verbose*} to @code{nil} while loading the file to avoid
|
||||
potentially verbose diagnostic messages printed on the standard
|
||||
output.
|
||||
@end itemize
|
||||
|
||||
@end table
|
||||
|
||||
@node Initialization Files
|
||||
@comment node-name, next, previous, up
|
||||
@node initialization files
|
||||
@section Initialization Files
|
||||
|
||||
SBCL processes initialization files with @code{read} and @code{eval},
|
||||
not @code{load}; hence initialization files can be used to set startup
|
||||
@code{*package*} and @code{*readtable*}, and for proclaiming a global
|
||||
optimization policy.
|
||||
@code{*package*} and @code{*readtable*}, and for proclaiming a global optimization
|
||||
policy.
|
||||
|
||||
@table @strong
|
||||
@itemize
|
||||
@item @strong{System Initialization File:} Defaults to @code{$SBCL_HOME/sbclrc},
|
||||
or if that doesn't exist to @code{/etc/sbclrc}. Can be overridden with
|
||||
the command line option @code{--sysinit} or @code{--no-sysinit} (see
|
||||
@ref{toplevel options}).
|
||||
|
||||
@item System Initialization File
|
||||
Defaults to @file{@env{$SBCL_HOME}/sbclrc}, or if that doesn't exist to
|
||||
@file{/etc/sbclrc}. Can be overridden with the command line option
|
||||
@code{--sysinit} or @code{--no-sysinit} (@pxref{Toplevel Options}).
|
||||
The system initialization file is intended for system
|
||||
administrators and software packagers to configure locations of
|
||||
installed third party modules, etc.
|
||||
|
||||
The system initialization file is intended for system administrators
|
||||
and software packagers to configure locations of installed third party
|
||||
modules, etc.
|
||||
@item @strong{User Initialization File:} Defaults to @code{$HOME/.sbclrc}. Can be
|
||||
overridden with the command line option @code{--userinit} or
|
||||
@code{--no-userinit} (see @ref{toplevel options}).
|
||||
|
||||
@item User Initialization File
|
||||
Defaults to @file{@env{$HOME}/.sbclrc}. Can be overridden with the
|
||||
command line option @code{--userinit} or @code{--no-userinit}
|
||||
(@pxref{Toplevel Options}).
|
||||
|
||||
The user initialization file is intended for personal customizations,
|
||||
such as loading certain modules at startup, defining convenience
|
||||
functions to use in the REPL, handling automatic recompilation
|
||||
of FASLs (@pxref{FASL Format}), etc.
|
||||
|
||||
@end table
|
||||
The user initialization file is intended for personal
|
||||
customizations, such as loading certain modules at startup,
|
||||
defining convenience functions to use in the REPL, handling
|
||||
automatic recompilation of FASLs (see @ref{fasl format}), etc.
|
||||
@end itemize
|
||||
|
||||
Neither initialization file is required.
|
||||
|
||||
@node Initialization and Exit Hooks
|
||||
@comment node-name, next, previous, up
|
||||
@node initialization and exit hooks
|
||||
@section Initialization and Exit Hooks
|
||||
|
||||
SBCL provides hooks into the system initialization and exit.
|
||||
|
||||
@include var-sb-ext-star-init-hooks-star.texinfo
|
||||
@include var-sb-ext-star-exit-hooks-star.texinfo
|
||||
@anchor{Variable sb-ext *init-hooks*}
|
||||
@vvindex @sortas{init-hooks* sb-ext} *init-hooks* [sb-ext]
|
||||
@deffn{Variable} sb-ext:*init-hooks*
|
||||
A list of function designators which are called in an unspecified
|
||||
order when a saved core image starts up, after the system itself has
|
||||
been initialized, but before non-user threads such as the finalizer
|
||||
thread have been started.
|
||||
|
||||
Unused by SBCL itself: reserved for user and applications.
|
||||
@end deffn
|
||||
@anchor{Variable sb-ext *exit-hooks*}
|
||||
@vvindex @sortas{exit-hooks* sb-ext} *exit-hooks* [sb-ext]
|
||||
@deffn{Variable} sb-ext:*exit-hooks*
|
||||
A list of function designators which are called in an unspecified
|
||||
order when SBCL process exits.
|
||||
|
||||
Unused by SBCL itself: reserved for user and applications.
|
||||
|
||||
Using (@code{sb-ext:exit} @code{:abort} @code{t}), or calling @code{exit(3)} directly circumvents
|
||||
these hooks.
|
||||
@end deffn
|
||||
|
|
|
|||
|
|
@ -1,202 +1,576 @@
|
|||
@node Streams
|
||||
@comment node-name, next, previous, up
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node streams
|
||||
@chapter Streams
|
||||
|
||||
@menu
|
||||
* Stream External Formats: stream external formats.
|
||||
* Bivalent Streams: bivalent streams.
|
||||
* Gray Streams: gray streams.
|
||||
* Simple Streams: sb simple streams.
|
||||
@end menu
|
||||
|
||||
Streams which read or write Lisp character data from or to the outside
|
||||
world -- files, sockets or other external entities -- require the
|
||||
specification of a conversion between the external, binary data and the
|
||||
Lisp characters. In ANSI Common Lisp, this is done by specifying the
|
||||
@code{:external-format} argument when the stream is created. The major
|
||||
information required is an @emph{encoding}, specified by a keyword
|
||||
naming that encoding; however, it is also possible to specify
|
||||
refinements to that encoding as additional options to the external
|
||||
format designator.
|
||||
specification of a conversion between the external, binary data and
|
||||
the Lisp characters. In ANSI Common Lisp, this is done by specifying
|
||||
the @code{:external-format} argument when the stream is created. The major
|
||||
information required is an @emph{encoding}, specified by a keyword naming
|
||||
that encoding; however, it is also possible to specify refinements
|
||||
to that encoding as additional options to the external format
|
||||
designator.
|
||||
|
||||
In addition, SBCL supports various extensions of ANSI Common Lisp
|
||||
streams:
|
||||
|
||||
@table @strong
|
||||
@item Bivalent Streams
|
||||
A type of stream that can read and write both @code{character} and
|
||||
@code{(unsigned-byte 8)} values.
|
||||
@itemize
|
||||
@item @emph{Bivalent Streams}: A type of stream that can read and write both
|
||||
@code{character} and @code{(unsigned-byte 8)} values.
|
||||
|
||||
@item Gray Streams
|
||||
User-overloadable CLOS classes whose instances can be used as Lisp
|
||||
streams (e.g. passed as the first argument to @code{format}).
|
||||
@item @emph{Gray Streams}: User-overloadable CLOS classes whose instances can
|
||||
be used as Lisp streams (e.g. passed as the first argument to
|
||||
@code{format}).
|
||||
|
||||
@item Simple Streams
|
||||
The bundled contrib module @dfn{sb-simple-streams} implements a subset
|
||||
of the Franz Allegro simple-streams proposal.
|
||||
@item @emph{Simple Streams}: The bundled contrib module @code{sb-simple-streams}
|
||||
implements a subset of the Franz Allegro simple-streams proposal.
|
||||
@end itemize
|
||||
|
||||
@end table
|
||||
|
||||
@menu
|
||||
* Stream External Formats::
|
||||
* Bivalent Streams::
|
||||
* Gray Streams::
|
||||
* Simple Streams::
|
||||
@end menu
|
||||
|
||||
@node Stream External Formats
|
||||
@node stream external formats
|
||||
@section Stream External Formats
|
||||
@cindex Stream External formats
|
||||
|
||||
@findex @cl{stream-external-format}
|
||||
The function @code{stream-external-format} returns the canonical name of
|
||||
the external format (See @ref{External Formats}) used by the stream for
|
||||
the external format (See @ref{external formats}) used by the stream for
|
||||
character-based input and/or output.
|
||||
|
||||
@findex @cl{open}
|
||||
@findex @cl{with-open-file}
|
||||
When constructing file streams, for example using @code{open} or
|
||||
@code{with-open-file}, the external format to use is specified via the
|
||||
@code{:external-format} argument which accepts an external format
|
||||
designator (See @ref{External Format Designators}).
|
||||
designator (see @ref{external format designators}).
|
||||
|
||||
@node Bivalent Streams
|
||||
@node bivalent streams
|
||||
@section Bivalent Streams
|
||||
|
||||
A @dfn{bivalent stream} can be used to read and write both
|
||||
@code{character} and @code{(unsigned-byte 8)} values. A bivalent
|
||||
stream is created by calling @code{open} with the argument @code{:element-type
|
||||
:default}. On such a stream, both binary and character data can be
|
||||
A @emph{bivalent stream} can be used to read and write both
|
||||
@code{character} and @code{(unsigned-byte 8)} values. A bivalent stream is
|
||||
created by calling @code{open} with the argument @code{:element-type}
|
||||
@code{:default}. On such a stream, both binary and character data can be
|
||||
read and written with the usual input and output functions.
|
||||
|
||||
@c Horrible visual markup
|
||||
@quotation
|
||||
Streams are @emph{not} created bivalent by default for performance
|
||||
reasons. Bivalent streams are incompatible with
|
||||
@code{fast-read-char}, an internal optimization in SBCL's stream
|
||||
machinery that bulk-converts octets to characters and implements a
|
||||
fast path through @code{read-char}.
|
||||
@end quotation
|
||||
reasons. Bivalent streams are incompatible with @code{fast-read-char}, an
|
||||
internal optimization in SBCL's stream machinery that bulk-converts
|
||||
octets to characters and implements a fast path through @code{read-char}.
|
||||
|
||||
@node Gray Streams
|
||||
@node gray streams
|
||||
@section Gray Streams
|
||||
|
||||
@menu
|
||||
* Gray Streams classes: gray streams classes.
|
||||
* Methods common to all streams: methods common to all streams.
|
||||
* Input stream methods: input stream methods.
|
||||
* Character input stream methods: character input stream methods.
|
||||
* Output stream methods: output stream methods.
|
||||
* Character output stream methods: character output stream methods.
|
||||
* Binary stream methods: binary stream methods.
|
||||
* Gray Streams Examples: gray streams examples.
|
||||
@end menu
|
||||
|
||||
The Gray Streams interface is a widely supported extension that
|
||||
provides for definition of CLOS-extensible stream classes. Gray
|
||||
stream classes are implemented by adding methods to generic functions
|
||||
analogous to Common Lisp's standard I/O functions. Instances of Gray
|
||||
stream classes may be used with any I/O operation where a non-Gray
|
||||
stream can, provided that all required methods have been implemented
|
||||
suitably.
|
||||
stream classes are implemented by adding methods to generic
|
||||
functions analogous to Common Lisp's standard I/O functions.
|
||||
Instances of Gray stream classes may be used with any I/O operation
|
||||
where a non-Gray stream can, provided that all required methods have
|
||||
been implemented suitably.
|
||||
|
||||
@menu
|
||||
* Gray Streams classes::
|
||||
* Methods common to all streams::
|
||||
* Input stream methods::
|
||||
* Character input stream methods::
|
||||
* Output stream methods::
|
||||
* Character output stream methods::
|
||||
* Binary stream methods::
|
||||
* Gray Streams examples::
|
||||
@end menu
|
||||
|
||||
@node Gray Streams classes
|
||||
@node gray streams classes
|
||||
@subsection Gray Streams classes
|
||||
|
||||
The defined Gray Stream classes are these:
|
||||
|
||||
@include class-sb-gray-fundamental-stream.texinfo
|
||||
@include class-sb-gray-fundamental-input-stream.texinfo
|
||||
@anchor{Class sb-gray fundamental-stream}
|
||||
@ttindex @sortas{fundamental-stream sb-gray} fundamental-stream [sb-gray]
|
||||
@deffn{Class} sb-gray:fundamental-stream
|
||||
Base class for all Gray streams.
|
||||
@end deffn
|
||||
@anchor{Class sb-gray fundamental-input-stream}
|
||||
@ttindex @sortas{fundamental-input-stream sb-gray} fundamental-input-stream [sb-gray]
|
||||
@deffn{Class} sb-gray:fundamental-input-stream
|
||||
Superclass of all Gray input streams.
|
||||
@end deffn
|
||||
The function @code{input-stream-p} will return true of any generalized
|
||||
instance of @code{sb-gray:fundamental-input-stream}.
|
||||
|
||||
@noindent
|
||||
The function input-stream-p will return true of any generalized
|
||||
instance of fundamental-input-stream.
|
||||
@anchor{Class sb-gray fundamental-output-stream}
|
||||
@ttindex @sortas{fundamental-output-stream sb-gray} fundamental-output-stream [sb-gray]
|
||||
@deffn{Class} sb-gray:fundamental-output-stream
|
||||
Superclass of all Gray output streams.
|
||||
@end deffn
|
||||
The function @code{output-stream-p} will return true of any generalized
|
||||
instance of @code{sb-gray:fundamental-output-stream}.
|
||||
|
||||
@include class-sb-gray-fundamental-output-stream.texinfo
|
||||
@anchor{Class sb-gray fundamental-binary-stream}
|
||||
@ttindex @sortas{fundamental-binary-stream sb-gray} fundamental-binary-stream [sb-gray]
|
||||
@deffn{Class} sb-gray:fundamental-binary-stream
|
||||
Superclass of all Gray streams whose element-type
|
||||
is a subtype of unsigned-byte or signed-byte.
|
||||
@end deffn
|
||||
Note that instantiable subclasses of @code{sb-gray:fundamental-binary-stream}
|
||||
should provide (or inherit) an applicable method for the generic
|
||||
function @code{stream-element-type}.
|
||||
|
||||
@noindent
|
||||
The function output-stream-p will return true of any generalized
|
||||
instance of fundamental-output-stream.
|
||||
|
||||
@include class-sb-gray-fundamental-binary-stream.texinfo
|
||||
|
||||
@noindent
|
||||
Note that instantiable subclasses of fundamental-binary-stream should
|
||||
provide (or inherit) an applicable method for the generic function
|
||||
stream-element-type.
|
||||
|
||||
@include class-sb-gray-fundamental-character-stream.texinfo
|
||||
@include class-sb-gray-fundamental-binary-input-stream.texinfo
|
||||
@include class-sb-gray-fundamental-binary-output-stream.texinfo
|
||||
@include class-sb-gray-fundamental-character-input-stream.texinfo
|
||||
@include class-sb-gray-fundamental-character-output-stream.texinfo
|
||||
|
||||
@node Methods common to all streams
|
||||
@anchor{Class sb-gray fundamental-character-stream}
|
||||
@ttindex @sortas{fundamental-character-stream sb-gray} fundamental-character-stream [sb-gray]
|
||||
@deffn{Class} sb-gray:fundamental-character-stream
|
||||
Superclass of all Gray streams whose element-type is a subtype of character.
|
||||
@end deffn
|
||||
@anchor{Class sb-gray fundamental-binary-input-stream}
|
||||
@ttindex @sortas{fundamental-binary-input-stream sb-gray} fundamental-binary-input-stream [sb-gray]
|
||||
@deffn{Class} sb-gray:fundamental-binary-input-stream
|
||||
Superclass of all Gray input streams whose element-type
|
||||
is a subtype of unsigned-byte or signed-byte.
|
||||
@end deffn
|
||||
@anchor{Class sb-gray fundamental-binary-output-stream}
|
||||
@ttindex @sortas{fundamental-binary-output-stream sb-gray} fundamental-binary-output-stream [sb-gray]
|
||||
@deffn{Class} sb-gray:fundamental-binary-output-stream
|
||||
Superclass of all Gray output streams whose element-type
|
||||
is a subtype of unsigned-byte or signed-byte.
|
||||
@end deffn
|
||||
@anchor{Class sb-gray fundamental-character-input-stream}
|
||||
@ttindex @sortas{fundamental-character-input-stream sb-gray} fundamental-character-input-stream [sb-gray]
|
||||
@deffn{Class} sb-gray:fundamental-character-input-stream
|
||||
Superclass of all Gray input streams whose element-type
|
||||
is a subtype of character.
|
||||
@end deffn
|
||||
@anchor{Class sb-gray fundamental-character-output-stream}
|
||||
@ttindex @sortas{fundamental-character-output-stream sb-gray} fundamental-character-output-stream [sb-gray]
|
||||
@deffn{Class} sb-gray:fundamental-character-output-stream
|
||||
Superclass of all Gray output streams whose element-type
|
||||
is a subtype of character.
|
||||
@end deffn
|
||||
@node methods common to all streams
|
||||
@subsection Methods common to all streams
|
||||
|
||||
These generic functions can be specialized on any generalized instance
|
||||
of fundamental-stream.
|
||||
|
||||
@include fun-common-lisp-stream-element-type.texinfo
|
||||
@include fun-common-lisp-close.texinfo
|
||||
@include fun-sb-gray-stream-file-position.texinfo
|
||||
|
||||
|
||||
|
||||
@node Input stream methods
|
||||
@anchor{Generic function common-lisp stream-element-type}
|
||||
@ffindex @sortas{stream-element-type common-lisp} stream-element-type [common-lisp]
|
||||
@deffn{Generic function} stream-element-type stream
|
||||
Return a type specifier for the kind of object returned by the
|
||||
@code{stream}. The class @code{sb-gray:fundamental-character-stream} provides a
|
||||
default method which returns @code{character}.
|
||||
@end deffn
|
||||
@anchor{Generic function common-lisp close}
|
||||
@ffindex @sortas{close common-lisp} close [common-lisp]
|
||||
@deffn{Generic function} close stream &key abort
|
||||
Close the given @code{stream}. No more I/O may be performed, but
|
||||
inquiries may still be made. If @code{:abort} is true, an attempt is made
|
||||
to clean up the side effects of having created the stream.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-file-position}
|
||||
@ffindex @sortas{stream-file-position sb-gray} stream-file-position [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-file-position stream &optional position-spec
|
||||
Used by @code{file-position}. Returns or changes the current position within @code{stream}.
|
||||
@end deffn
|
||||
@node input stream methods
|
||||
@subsection Input stream methods
|
||||
|
||||
These generic functions may be specialized on any generalized instance
|
||||
of fundamental-input-stream.
|
||||
|
||||
@include fun-sb-gray-stream-clear-input.texinfo
|
||||
@include fun-sb-gray-stream-read-sequence.texinfo
|
||||
|
||||
@node Character input stream methods
|
||||
@anchor{Generic function sb-gray stream-clear-input}
|
||||
@ffindex @sortas{stream-clear-input sb-gray} stream-clear-input [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-clear-input stream
|
||||
This is like @code{cl:clear-input}, but for Gray streams, returning @code{nil}.
|
||||
The default method does nothing.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-read-sequence}
|
||||
@ffindex @sortas{stream-read-sequence sb-gray} stream-read-sequence [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-read-sequence stream seq &optional start end
|
||||
This is like @code{cl:read-sequence}, but for Gray streams.
|
||||
@end deffn
|
||||
@node character input stream methods
|
||||
@subsection Character input stream methods
|
||||
|
||||
These generic functions are used to implement subclasses of
|
||||
fundamental-input-stream:
|
||||
@code{sb-gray:fundamental-input-stream}:
|
||||
|
||||
@include fun-sb-gray-stream-peek-char.texinfo
|
||||
@include fun-sb-gray-stream-read-char-no-hang.texinfo
|
||||
@include fun-sb-gray-stream-read-char.texinfo
|
||||
@include fun-sb-gray-stream-read-line.texinfo
|
||||
@include fun-sb-gray-stream-listen.texinfo
|
||||
@include fun-sb-gray-stream-unread-char.texinfo
|
||||
|
||||
@node Output stream methods
|
||||
@anchor{Generic function sb-gray stream-peek-char}
|
||||
@ffindex @sortas{stream-peek-char sb-gray} stream-peek-char [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-peek-char stream
|
||||
This is used to implement @code{peek-char}; this corresponds to @code{peek-type}
|
||||
of @code{nil}. It returns either a character or @code{:eof}. The default method
|
||||
calls @code{stream-read-char} and @code{stream-unread-char}.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-read-char-no-hang}
|
||||
@ffindex @sortas{stream-read-char-no-hang sb-gray} stream-read-char-no-hang [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-read-char-no-hang stream
|
||||
This is used to implement @code{read-char-no-hang}. It returns either a
|
||||
character, or @code{nil} if no input is currently available, or @code{:eof} if
|
||||
end-of-file is reached. The default method provided by
|
||||
@code{fundamental-character-input-stream} simply calls @code{stream-read-char}; this
|
||||
is sufficient for file streams, but interactive streams should define
|
||||
their own method.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-read-char}
|
||||
@ffindex @sortas{stream-read-char sb-gray} stream-read-char [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-read-char stream
|
||||
Read one character from the stream. Return either a
|
||||
character object, or the symbol @code{:eof} if the stream is at end-of-file.
|
||||
Every subclass of @code{fundamental-character-input-stream} must define a
|
||||
method for this function.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-read-line}
|
||||
@ffindex @sortas{stream-read-line sb-gray} stream-read-line [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-read-line stream
|
||||
This is used by @code{read-line}. A string is returned as the first value. The
|
||||
second value is true if the string was terminated by end-of-file
|
||||
instead of the end of a line. The default method uses repeated
|
||||
calls to @code{stream-read-char}.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-listen}
|
||||
@ffindex @sortas{stream-listen sb-gray} stream-listen [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-listen stream
|
||||
This is used by @code{listen}. It returns true or false. The default method uses
|
||||
@code{stream-read-char-no-hang} and @code{stream-unread-char}. Most streams should
|
||||
define their own method since it will usually be trivial and will
|
||||
always be more efficient than the default method.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-unread-char}
|
||||
@ffindex @sortas{stream-unread-char sb-gray} stream-unread-char [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-unread-char stream character
|
||||
Undo the last call to @code{stream-read-char}, as in @code{unread-char}.
|
||||
Return @code{nil}. Every subclass of @code{fundamental-character-input-stream}
|
||||
must define a method for this function.
|
||||
@end deffn
|
||||
@node output stream methods
|
||||
@subsection Output stream methods
|
||||
|
||||
These generic functions are used to implement subclasses of
|
||||
fundamental-output-stream:
|
||||
@code{sb-gray:fundamental-output-stream}:
|
||||
|
||||
@include fun-sb-gray-stream-clear-output.texinfo
|
||||
@include fun-sb-gray-stream-finish-output.texinfo
|
||||
@include fun-sb-gray-stream-force-output.texinfo
|
||||
@include fun-sb-gray-stream-write-sequence.texinfo
|
||||
|
||||
@node Character output stream methods
|
||||
@anchor{Generic function sb-gray stream-clear-output}
|
||||
@ffindex @sortas{stream-clear-output sb-gray} stream-clear-output [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-clear-output stream
|
||||
This is like @code{cl:clear-output}, but for Gray streams: clear the given
|
||||
output @code{stream}. The default method does nothing.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-finish-output}
|
||||
@ffindex @sortas{stream-finish-output sb-gray} stream-finish-output [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-finish-output stream
|
||||
Attempts to ensure that all output sent to the Stream has reached
|
||||
its destination, and only then returns false. Implements
|
||||
@code{finish-output}. The default method does nothing.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-force-output}
|
||||
@ffindex @sortas{stream-force-output sb-gray} stream-force-output [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-force-output stream
|
||||
Attempts to force any buffered output to be sent. Implements
|
||||
@code{force-output}. The default method does nothing.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-write-sequence}
|
||||
@ffindex @sortas{stream-write-sequence sb-gray} stream-write-sequence [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-write-sequence stream seq &optional start end
|
||||
This is like @code{cl:write-sequence}, but for Gray streams.
|
||||
@end deffn
|
||||
@node character output stream methods
|
||||
@subsection Character output stream methods
|
||||
|
||||
These generic functions are used to implement subclasses of
|
||||
fundamental-character-output-stream:
|
||||
@code{sb-gray:fundamental-character-output-stream}:
|
||||
|
||||
@include fun-sb-gray-stream-advance-to-column.texinfo
|
||||
@include fun-sb-gray-stream-fresh-line.texinfo
|
||||
@include fun-sb-gray-stream-line-column.texinfo
|
||||
@include fun-sb-gray-stream-line-length.texinfo
|
||||
@include fun-sb-gray-stream-start-line-p.texinfo
|
||||
@include fun-sb-gray-stream-terpri.texinfo
|
||||
@include fun-sb-gray-stream-write-char.texinfo
|
||||
@include fun-sb-gray-stream-write-string.texinfo
|
||||
|
||||
@node Binary stream methods
|
||||
@anchor{Generic function sb-gray stream-advance-to-column}
|
||||
@ffindex @sortas{stream-advance-to-column sb-gray} stream-advance-to-column [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-advance-to-column stream column
|
||||
Write enough blank space so that the next character will be
|
||||
written at the specified column. Returns true if the operation is
|
||||
successful, or @code{nil} if it is not supported for this stream. This is
|
||||
intended for use by by @code{pprint} and @code{format} ~T. The default method
|
||||
uses @code{stream-line-column} and repeated calls to @code{stream-write-char}
|
||||
with a #SPACE character; it returns @code{nil} if @code{stream-line-column}
|
||||
returns @code{nil}.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-fresh-line}
|
||||
@ffindex @sortas{stream-fresh-line sb-gray} stream-fresh-line [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-fresh-line stream
|
||||
Outputs a new line to the Stream if it is not positioned at the
|
||||
beginning of a line. Returns @code{t} if it output a new line, nil
|
||||
otherwise. Used by @code{fresh-line}. The default method uses
|
||||
@code{stream-start-line-p} and @code{stream-terpri}.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-line-column}
|
||||
@ffindex @sortas{stream-line-column sb-gray} stream-line-column [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-line-column stream
|
||||
Return the column number where the next character
|
||||
will be written, or @code{nil} if that is not meaningful for this stream.
|
||||
The first column on a line is numbered 0. This function is used in
|
||||
the implementation of @code{pprint} and the @code{format} ~T directive. For every
|
||||
character output stream class that is defined, a method must be
|
||||
defined for this function, although it is permissible for it to
|
||||
always return @code{nil}.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-line-length}
|
||||
@ffindex @sortas{stream-line-length sb-gray} stream-line-length [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-line-length stream
|
||||
Return the stream line length or @code{nil}.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-start-line-p}
|
||||
@ffindex @sortas{stream-start-line-p sb-gray} stream-start-line-p [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-start-line-p stream
|
||||
Is @code{stream} known to be positioned at the beginning of a line?
|
||||
It is permissible for an implementation to always return
|
||||
@code{nil}. This is used in the implementation of @code{fresh-line}. Note that
|
||||
while a value of 0 from @code{stream-line-column} also indicates the
|
||||
beginning of a line, there are cases where @code{stream-start-line-p} can be
|
||||
meaningfully implemented although @code{stream-line-column} can't be. For
|
||||
example, for a window using variable-width characters, the column
|
||||
number isn't very meaningful, but the beginning of the line does have
|
||||
a clear meaning. The default method for @code{stream-start-line-p} on class
|
||||
@code{fundamental-character-output-stream} uses @code{stream-line-column}, so if
|
||||
that is defined to return @code{nil}, then a method should be provided for
|
||||
either @code{stream-start-line-p} or @code{stream-fresh-line}.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-terpri}
|
||||
@ffindex @sortas{stream-terpri sb-gray} stream-terpri [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-terpri stream
|
||||
Writes an end of line, as for @code{terpri}. Returns @code{nil}. The default
|
||||
method does (@code{stream-write-char} stream @code{#\Newline}).
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-write-char}
|
||||
@ffindex @sortas{stream-write-char sb-gray} stream-write-char [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-write-char stream character
|
||||
Write @code{character} to @code{stream} and return @code{character}. Every
|
||||
subclass of @code{fundamental-character-output-stream} must have a method
|
||||
defined for this function.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-write-string}
|
||||
@ffindex @sortas{stream-write-string sb-gray} stream-write-string [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-write-string stream string &optional start end
|
||||
This is used by @code{write-string}. It writes the string to the stream,
|
||||
optionally delimited by start and end, which default to 0 and @code{nil}.
|
||||
The string argument is returned. The default method provided by
|
||||
@code{fundamental-character-output-stream} uses repeated calls to
|
||||
@code{stream-write-char}.
|
||||
@end deffn
|
||||
@node binary stream methods
|
||||
@subsection Binary stream methods
|
||||
|
||||
The following generic functions are available for subclasses of
|
||||
fundamental-binary-stream:
|
||||
@code{sb-gray:fundamental-binary-stream}:
|
||||
|
||||
@include fun-sb-gray-stream-read-byte.texinfo
|
||||
@include fun-sb-gray-stream-write-byte.texinfo
|
||||
@anchor{Generic function sb-gray stream-read-byte}
|
||||
@ffindex @sortas{stream-read-byte sb-gray} stream-read-byte [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-read-byte stream
|
||||
Used by @code{read-byte}; returns either an integer, or the symbol @code{:eof}
|
||||
if the stream is at end-of-file.
|
||||
@end deffn
|
||||
@anchor{Generic function sb-gray stream-write-byte}
|
||||
@ffindex @sortas{stream-write-byte sb-gray} stream-write-byte [sb-gray]
|
||||
@deffn{Generic function} sb-gray:stream-write-byte stream integer
|
||||
Implements @code{write-byte}; writes the integer to the stream and
|
||||
returns the integer as the result.
|
||||
@end deffn
|
||||
@node gray streams examples
|
||||
@subsection Gray Streams Examples
|
||||
|
||||
@include gray-streams-examples.texinfo
|
||||
@menu
|
||||
* Character Counting Input Stream: character counting input stream.
|
||||
* Output Prefixing Character Stream: output prefixing character stream.
|
||||
@end menu
|
||||
|
||||
@node Simple Streams
|
||||
@comment node-name, next, previous, up
|
||||
@section Simple Streams
|
||||
@include sb-simple-streams/sb-simple-streams.texinfo
|
||||
Below are two classes of stream that can be conveniently defined as
|
||||
wrappers for Common Lisp streams. These are meant to serve as
|
||||
examples of minimal implementations of the protocols that must be
|
||||
followed when defining Gray streams. Realistic uses of the Gray
|
||||
Streams API would implement the various methods that can do I/O in
|
||||
batches, such as @code{sb-gray:stream-read-line},
|
||||
@code{sb-gray:stream-write-string}, @code{sb-gray:stream-read-sequence}, and
|
||||
@code{sb-gray:stream-write-sequence}.
|
||||
|
||||
@node character counting input stream
|
||||
@subsubsection Character Counting Input Stream
|
||||
|
||||
It is occasionally handy for programs that process input files to
|
||||
count the number of characters and lines seen so far, and the number
|
||||
of characters seen on the current line, so that useful messages may
|
||||
be reported in case of parsing errors, etc. Here is a character
|
||||
input stream class that keeps track of these counts. Note that all
|
||||
character input streams must implement @code{sb-gray:stream-read-char} and
|
||||
@code{sb-gray:stream-unread-char}.
|
||||
|
||||
@example
|
||||
(defclass wrapped-stream (fundamental-stream)
|
||||
((stream :initarg :stream :reader stream-of)))
|
||||
|
||||
(defmethod stream-element-type ((stream wrapped-stream))
|
||||
(stream-element-type (stream-of stream)))
|
||||
|
||||
(defmethod close ((stream wrapped-stream) &key abort)
|
||||
(close (stream-of stream) :abort abort))
|
||||
|
||||
(defclass wrapped-character-input-stream
|
||||
(wrapped-stream fundamental-character-input-stream)
|
||||
())
|
||||
|
||||
(defmethod stream-read-char ((stream wrapped-character-input-stream))
|
||||
(read-char (stream-of stream) nil :eof))
|
||||
|
||||
(defmethod stream-unread-char ((stream wrapped-character-input-stream)
|
||||
char)
|
||||
(unread-char char (stream-of stream)))
|
||||
|
||||
(defclass counting-character-input-stream
|
||||
(wrapped-character-input-stream)
|
||||
((char-count :initform 1 :accessor char-count-of)
|
||||
(line-count :initform 1 :accessor line-count-of)
|
||||
(col-count :initform 1 :accessor col-count-of)
|
||||
(prev-col-count :initform 1 :accessor prev-col-count-of)))
|
||||
|
||||
(defmethod stream-read-char ((stream counting-character-input-stream))
|
||||
(with-accessors ((inner-stream stream-of) (chars char-count-of)
|
||||
(lines line-count-of) (cols col-count-of)
|
||||
(prev prev-col-count-of)) stream
|
||||
(let ((char (call-next-method)))
|
||||
(cond ((eql char :eof)
|
||||
:eof)
|
||||
((char= char #Newline)
|
||||
(incf lines)
|
||||
(incf chars)
|
||||
(setf prev cols)
|
||||
(setf cols 1)
|
||||
char)
|
||||
(t
|
||||
(incf chars)
|
||||
(incf cols)
|
||||
char)))))
|
||||
|
||||
(defmethod stream-unread-char ((stream counting-character-input-stream)
|
||||
char)
|
||||
(with-accessors ((inner-stream stream-of) (chars char-count-of)
|
||||
(lines line-count-of) (cols col-count-of)
|
||||
(prev prev-col-count-of)) stream
|
||||
(cond ((char= char #Newline)
|
||||
(decf lines)
|
||||
(decf chars)
|
||||
(setf cols prev))
|
||||
(t
|
||||
(decf chars)
|
||||
(decf cols)
|
||||
char))
|
||||
(call-next-method)))
|
||||
@end example
|
||||
|
||||
The default methods for @code{sb-gray:stream-read-char-no-hang},
|
||||
@code{sb-gray:stream-peek-char}, @code{sb-gray:stream-listen},
|
||||
@code{sb-gray:stream-clear-input}, @code{sb-gray:stream-read-line}, and
|
||||
@code{sb-gray:stream-read-sequence} should be sufficient (though the last
|
||||
two will probably be slower than methods that forwarded directly).
|
||||
|
||||
Here's a sample use of this class:
|
||||
|
||||
@example
|
||||
(with-input-from-string (input "1 2
|
||||
3 :foo ")
|
||||
(let ((counted-stream (make-instance 'counting-character-input-stream
|
||||
:stream input)))
|
||||
(loop for thing = (read counted-stream) while thing
|
||||
unless (numberp thing) do
|
||||
(error "Non-number ~S (line ~D, column ~D)" thing
|
||||
(line-count-of counted-stream)
|
||||
(- (col-count-of counted-stream)
|
||||
(length (format nil "~S" thing))))
|
||||
end
|
||||
do (print thing))))
|
||||
@end example
|
||||
|
||||
Output:
|
||||
|
||||
@example
|
||||
1
|
||||
2
|
||||
3
|
||||
Non-number :FOO (line 2, column 5)
|
||||
[Condition of type SIMPLE-ERROR]
|
||||
@end example
|
||||
|
||||
@node output prefixing character stream
|
||||
@subsubsection Output Prefixing Character Stream
|
||||
|
||||
One use for a wrapped output stream might be to prefix each line of
|
||||
text with a timestamp, e.g. for a logging stream. Here's a simple
|
||||
stream that does this, though without any fancy line-wrapping. Note
|
||||
that all character output stream classes must implement
|
||||
@code{sb-gray:stream-write-char} and @code{sb-gray:stream-line-column}.
|
||||
|
||||
@example
|
||||
(defclass wrapped-stream (fundamental-stream)
|
||||
((stream :initarg :stream :reader stream-of)))
|
||||
|
||||
(defmethod stream-element-type ((stream wrapped-stream))
|
||||
(stream-element-type (stream-of stream)))
|
||||
|
||||
(defmethod close ((stream wrapped-stream) &key abort)
|
||||
(close (stream-of stream) :abort abort))
|
||||
|
||||
(defclass wrapped-character-output-stream
|
||||
(wrapped-stream fundamental-character-output-stream)
|
||||
((col-index :initform 0 :accessor col-index-of)))
|
||||
|
||||
(defmethod stream-line-column ((stream wrapped-character-output-stream))
|
||||
(col-index-of stream))
|
||||
|
||||
(defmethod stream-write-char ((stream wrapped-character-output-stream)
|
||||
char)
|
||||
(with-accessors ((inner-stream stream-of) (cols col-index-of)) stream
|
||||
(write-char char inner-stream)
|
||||
(if (char= char #Newline)
|
||||
(setf cols 0)
|
||||
(incf cols))))
|
||||
|
||||
(defclass prefixed-character-output-stream
|
||||
(wrapped-character-output-stream)
|
||||
((prefix :initarg :prefix :reader prefix-of)))
|
||||
|
||||
(defgeneric write-prefix (prefix stream)
|
||||
(:method ((prefix string) stream) (write-string prefix stream))
|
||||
(:method ((prefix function) stream) (funcall prefix stream)))
|
||||
|
||||
(defmethod stream-write-char ((stream prefixed-character-output-stream)
|
||||
char)
|
||||
(with-accessors ((inner-stream stream-of) (cols col-index-of)
|
||||
(prefix prefix-of)) stream
|
||||
(when (zerop cols)
|
||||
(write-prefix prefix inner-stream))
|
||||
(call-next-method)))
|
||||
@end example
|
||||
|
||||
As with the example input stream, this implements only the minimal
|
||||
protocol. A production implementation should also provide methods
|
||||
for at least @code{sb-gray:stream-write-string},
|
||||
@code{sb-gray:stream-write-sequence}.
|
||||
|
||||
And here's a sample use of this class:
|
||||
|
||||
@example
|
||||
(flet ((format-timestamp (stream)
|
||||
(apply #'format stream "[~2@@*~2,' D:~1@@*~2,'0D:~0@@*~2,'0D] "
|
||||
(multiple-value-list (get-decoded-time)))))
|
||||
(let ((output (make-instance 'prefixed-character-output-stream
|
||||
:stream *standard-output*
|
||||
:prefix #'format-timestamp)))
|
||||
(loop for string in '("abc" "def" ")ghi") do
|
||||
(write-line string output)
|
||||
(sleep 1))))
|
||||
@end example
|
||||
|
||||
Output:
|
||||
|
||||
@example
|
||||
[ 0:30:05] abc
|
||||
[ 0:30:06] def
|
||||
[ 0:30:07] ghi
|
||||
NIL
|
||||
@end example
|
||||
|
||||
@include ../../contrib/sb-simple-streams/sb-simple-streams.texinfo
|
||||
|
|
|
|||
|
|
@ -1,23 +1,23 @@
|
|||
@node Getting Support and Reporting Bugs
|
||||
@comment node-name, next, previous, up
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node support and bugs
|
||||
@chapter Getting Support and Reporting Bugs
|
||||
|
||||
@menu
|
||||
* Volunteer Support::
|
||||
* Commercial Support::
|
||||
* Reporting Bugs::
|
||||
* Volunteer Support: volunteer support.
|
||||
* Commercial Support: commercial support.
|
||||
* Reporting Bugs: reporting bugs.
|
||||
@end menu
|
||||
|
||||
@node Volunteer Support
|
||||
@comment node-name, next, previous, up
|
||||
@node volunteer support
|
||||
@section Volunteer Support
|
||||
|
||||
Your primary source of SBCL support should probably be the mailing
|
||||
list @strong{sbcl-help}: in addition to other users SBCL developers
|
||||
monitor this list and are available for advice. As an anti-spam
|
||||
measure subscription is required for posting:
|
||||
list @code{sbcl-help}: in addition to other users SBCL developers monitor
|
||||
this list and are available for advice. As an anti-spam measure
|
||||
subscription is required for posting:
|
||||
|
||||
@urlline{https://lists.sourceforge.net/lists/listinfo/sbcl-help}
|
||||
@url{https://lists.sourceforge.net/lists/listinfo/sbcl-help}
|
||||
|
||||
Remember that the people answering your question are volunteers, so
|
||||
you stand a much better chance of getting a good answer if you ask a
|
||||
|
|
@ -25,22 +25,21 @@ good question.
|
|||
|
||||
Before sending mail, check the list archives at either
|
||||
|
||||
@urlline{http://sourceforge.net/mailarchive/forum.php?forum_name=sbcl-help}
|
||||
@url{http://sourceforge.net/mailarchive/forum.php?forum_name=sbcl-help}
|
||||
|
||||
or
|
||||
|
||||
@urlline{http://news.gmane.org/gmane.lisp.steel-bank.general}
|
||||
@url{http://news.gmane.org/gmane.lisp.steel-bank.general}
|
||||
|
||||
to see if your question has been answered already. Checking the bug
|
||||
database is also worth it @xref{Reporting Bugs}, to see if the issue
|
||||
database is also worth it (see @ref{reporting bugs}), to see if the issue
|
||||
is already known.
|
||||
|
||||
For general advice on asking good questions, see
|
||||
|
||||
@urlline{http://www.catb.org/~esr/faqs/smart-questions.html}.
|
||||
@url{http://www.catb.org/~esr/faqs/smart-questions.html}.
|
||||
|
||||
@node Commercial Support
|
||||
@comment node-name, next, previous, up
|
||||
@node commercial support
|
||||
@section Commercial Support
|
||||
|
||||
There is no formal organization developing SBCL, but if you need a
|
||||
|
|
@ -49,31 +48,36 @@ list of companies and consultants below. Use it to identify service
|
|||
providers with appropriate skills and interests, and contact them
|
||||
directly.
|
||||
|
||||
The SBCL project cannot verify the accuracy of the information or the
|
||||
competence of the people listed, and they have provided their own
|
||||
blurbs below: you must make your own judgement of suitability from the
|
||||
available information - refer to the links they provide, the CREDITS
|
||||
file, mailing list archives, CVS commit messages, and so on. Please
|
||||
feel free to ask for advice on the sbcl-help list.
|
||||
The SBCL project cannot verify the accuracy of the information or
|
||||
the competence of the people listed, and they have provided their
|
||||
own blurbs below: you must make your own judgement of suitability
|
||||
from the available information - refer to the links they provide,
|
||||
the CREDITS file, mailing list archives, CVS commit messages, and so
|
||||
on. Please feel free to ask for advice on the sbcl-help list.
|
||||
|
||||
(At present, no companies or consultants wish to advertise paid support
|
||||
or custom SBCL development in this manual).
|
||||
(At present, no companies or consultants wish to advertise paid
|
||||
support or custom SBCL development in this manual).
|
||||
|
||||
@node Reporting Bugs
|
||||
@comment node-name, next, previous, up
|
||||
@node reporting bugs
|
||||
@section Reporting Bugs
|
||||
|
||||
@menu
|
||||
* How to Report Bugs Effectively: how to report bugs effectively.
|
||||
* How to Report Signal-related Bugs: how to report signal related bugs.
|
||||
@end menu
|
||||
|
||||
SBCL uses Launchpad to track bugs. The bug database is available at
|
||||
|
||||
@urlline{https://bugs.launchpad.net/sbcl}
|
||||
@url{https://bugs.launchpad.net/sbcl}
|
||||
|
||||
Reporting bugs there requires registering at Launchpad. However, bugs
|
||||
can also be reported on the mailing list @strong{sbcl-bugs}, which is
|
||||
moderated but does @emph{not} require subscribing.
|
||||
Reporting bugs there requires registering at Launchpad. However,
|
||||
bugs can also be reported on the mailing list @code{sbcl-bugs},
|
||||
which is moderated but does @emph{not} require subscribing.
|
||||
|
||||
Simply send email to @email{sbcl-bugs@@lists.sourceforge.net} and the
|
||||
bug will be checked and added to Launchpad by SBCL maintainers.
|
||||
Simply send email to @code{sbcl-bugs@@lists.sourceforge.net} and the bug
|
||||
will be checked and added to Launchpad by SBCL maintainers.
|
||||
|
||||
@node how to report bugs effectively
|
||||
@subsection How to Report Bugs Effectively
|
||||
|
||||
Please include enough information in a bug report that someone reading
|
||||
|
|
@ -99,52 +103,43 @@ then at the command line type
|
|||
the program loops endlessly instead of printing the object.
|
||||
@end example
|
||||
|
||||
A more in-depth discussion on reporting bugs effectively can be found
|
||||
at
|
||||
A more in-depth discussion on reporting bugs effectively can be
|
||||
found at
|
||||
|
||||
@urlline{http://www.chiark.greenend.org.uk/~sgtatham/bugs.html}.
|
||||
@url{http://www.chiark.greenend.org.uk/~sgtatham/bugs.html}.
|
||||
|
||||
@subsection Signal Related Bugs
|
||||
@node how to report signal related bugs
|
||||
@subsection How to Report Signal-related Bugs
|
||||
|
||||
If you run into a signal related bug, you are getting fatal errors
|
||||
such as @code{signal N is [un]blocked} or just hangs, and you want to
|
||||
send a useful bug report then:
|
||||
|
||||
@enumerate
|
||||
@itemize
|
||||
@item Compile SBCL with ldb enabled (feature @code{:sb-ldb}, see
|
||||
@code{base-target-features.lisp-expr}).
|
||||
|
||||
@item
|
||||
@cindex ldb
|
||||
Compile SBCL with ldb enabled (feature @code{:sb-ldb}, see
|
||||
@file{base-target-features.lisp-expr}).
|
||||
@item Isolate a smallish test case, run it.
|
||||
|
||||
@item
|
||||
Isolate a smallish test case, run it.
|
||||
@item If it just hangs kill it with @code{sigabrt}: @code{kill -ABRT <pidof sbcl>}.
|
||||
|
||||
@item
|
||||
If it just hangs kill it with sigabrt: @code{kill -ABRT <pidof sbcl>}.
|
||||
@item Print the backtrace from ldb by typing @code{ba}.
|
||||
|
||||
@item
|
||||
Print the backtrace from ldb by typing @code{ba}.
|
||||
@item Attach gdb: @code{gdb -p <pidof sbcl>} and get backtraces for all
|
||||
threads: @code{thread apply all ba}.
|
||||
|
||||
@item
|
||||
Attach gdb: @code{gdb -p <pidof sbcl>} and get backtraces for all threads:
|
||||
@code{thread apply all ba}.
|
||||
@item If multiple threads are in play then still in gdb, try to get Lisp
|
||||
backtrace for all threads: @code{thread apply all call
|
||||
backtrace_from_fp($ebp, 100, 0)}. Substitute @code{$ebp} with @code{$rbp} on
|
||||
x86-64. The backtraces will appear in the stdout of the SBCL
|
||||
process.
|
||||
|
||||
@item
|
||||
If multiple threads are in play then still in gdb, try to get Lisp
|
||||
backtrace for all threads: @code{thread apply all call
|
||||
backtrace_from_fp($ebp, 100, 0)}. Substitute @code{$ebp} with @code{$rbp}
|
||||
on x86-64. The backtraces will appear in the stdout of the SBCL
|
||||
process.
|
||||
@item Send a report with the backtraces and the output (both stdout and
|
||||
stderr) produced by SBCL.
|
||||
|
||||
@item
|
||||
Send a report with the backtraces and the output (both stdout and
|
||||
stderr) produced by SBCL.
|
||||
@item Don't forget to include OS and SBCL version.
|
||||
|
||||
@item
|
||||
Don't forget to include OS and SBCL version.
|
||||
@item If available, include information on outcome of the same test with
|
||||
other versions of SBCL, OS, ...
|
||||
@end itemize
|
||||
|
||||
@item
|
||||
If available, include information on outcome of the same test with
|
||||
other versions of SBCL, OS, ...
|
||||
@end enumerate
|
||||
|
|
|
|||
File diff suppressed because it is too large
Load diff
|
|
@ -1,28 +1,29 @@
|
|||
@node Timers
|
||||
@comment node-name, next, previous, up
|
||||
@c Generated by the sb-manual contrib. Do not edit.
|
||||
|
||||
@node timers
|
||||
@chapter Timers
|
||||
|
||||
SBCL supports a system-wide event scheduler implemented on top of
|
||||
@code{setitimer} that also works with threads but does not require a
|
||||
@code{setitimer(2)} that also works with threads but does not require a
|
||||
separate scheduler thread.
|
||||
|
||||
The following example schedules a timer that writes ``Hello, world'' after
|
||||
two seconds.
|
||||
The following example schedules a timer that writes @code{Hello, world}
|
||||
after two seconds.
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(schedule-timer (make-timer (lambda ()
|
||||
(write-line "Hello, world")
|
||||
(force-output)))
|
||||
2)
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
It should be noted that writing timer functions requires special care,
|
||||
as the dynamic environment in which they run is unpredictable: dynamic
|
||||
variable bindings, locks held, etc, all depend on whatever code was
|
||||
running when the timer fired. The following example should serve as
|
||||
a cautionary tale:
|
||||
It should be noted that writing timer functions requires special
|
||||
care, as the dynamic environment in which they run is unpredictable:
|
||||
dynamic variable bindings, locks held, etc, all depend on whatever
|
||||
code was running when the timer fired. The following example should
|
||||
serve as a cautionary tale:
|
||||
|
||||
@lisp
|
||||
@example
|
||||
(defvar *foo* nil)
|
||||
|
||||
(defun show-foo ()
|
||||
|
|
@ -36,14 +37,64 @@ a cautionary tale:
|
|||
(sleep 1.0))
|
||||
(let ((*foo* :surprise!))
|
||||
(sleep 2.0)))
|
||||
@end lisp
|
||||
@end example
|
||||
|
||||
@section Timer Dictionary
|
||||
@anchor{Structure sb-ext timer}
|
||||
@ttindex @sortas{timer sb-ext} timer [sb-ext]
|
||||
@deffn{Structure} sb-ext:timer
|
||||
Timer type. Do not rely on timers being structs as it may change in
|
||||
future versions.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext make-timer}
|
||||
@ffindex @sortas{make-timer sb-ext} make-timer [sb-ext]
|
||||
@deffn{Function} sb-ext:make-timer function &key name thread
|
||||
Create a timer that runs @code{function} when triggered.
|
||||
|
||||
@include struct-sb-ext-timer.texinfo
|
||||
@include fun-sb-ext-make-timer.texinfo
|
||||
@include fun-sb-ext-timer-name.texinfo
|
||||
@include fun-sb-ext-timer-scheduled-p.texinfo
|
||||
@include fun-sb-ext-schedule-timer.texinfo
|
||||
@include fun-sb-ext-unschedule-timer.texinfo
|
||||
@include fun-sb-ext-list-all-timers.texinfo
|
||||
If a @code{thread} is supplied, @code{function} is run in that thread. If @code{thread} is
|
||||
@code{t}, a new thread is created for @code{function} each time the timer is
|
||||
triggered. If @code{thread} is @code{nil}, @code{function} is run in an unspecified thread.
|
||||
|
||||
When @code{thread} is not @code{t}, @code{sb-thread:interrupt-thread} is used to run
|
||||
@code{function} and the ordering guarantees of @code{sb-thread:interrupt-thread}
|
||||
apply. In that case, @code{function} runs with interrupts disabled but
|
||||
@code{with-interrupts} is allowed.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext timer-name}
|
||||
@ffindex @sortas{timer-name sb-ext} timer-name [sb-ext]
|
||||
@deffn{Function} sb-ext:timer-name timer
|
||||
Return the name of @code{timer}.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext timer-scheduled-p}
|
||||
@ffindex @sortas{timer-scheduled-p sb-ext} timer-scheduled-p [sb-ext]
|
||||
@deffn{Function} sb-ext:timer-scheduled-p timer &key delta
|
||||
See if @code{timer} will still need to be triggered after @code{delta} seconds
|
||||
from now. For timers with a repeat interval it returns true.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext schedule-timer}
|
||||
@ffindex @sortas{schedule-timer sb-ext} schedule-timer [sb-ext]
|
||||
@deffn{Function} sb-ext:schedule-timer timer time &key repeat-interval absolute-p catch-up
|
||||
Schedule @code{timer} to be triggered at @code{time}. If @code{absolute-p} then @code{time} is
|
||||
universal time, but non-integral values are also allowed, else @code{time} is
|
||||
measured as the number of seconds from the current time.
|
||||
|
||||
If @code{repeat-interval} is given, @code{timer} is automatically rescheduled upon
|
||||
expiry.
|
||||
|
||||
If @code{repeat-interval} is non-@code{nil}, the Boolean @code{catch-up} controls whether
|
||||
@code{timer} will "catch up" by repeatedly calling its function without
|
||||
delay in case calls are missed because of a clock discontinuity such
|
||||
as a suspend and resume cycle of the computer. The default is @code{nil},
|
||||
i.e. do not catch up.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext unschedule-timer}
|
||||
@ffindex @sortas{unschedule-timer sb-ext} unschedule-timer [sb-ext]
|
||||
@deffn{Function} sb-ext:unschedule-timer timer
|
||||
Cancel @code{timer}. Once this function returns it is guaranteed that
|
||||
@code{timer} shall not be triggered again and there are no unfinished
|
||||
triggers.
|
||||
@end deffn
|
||||
@anchor{Function sb-ext list-all-timers}
|
||||
@ffindex @sortas{list-all-timers sb-ext} list-all-timers [sb-ext]
|
||||
@deffn{Function} sb-ext:list-all-timers
|
||||
Return a list of all timers in the system.
|
||||
@end deffn
|
||||
|
|
|
|||
Loading…
Reference in a new issue