[Larceny-users] Larceny basics
Felix
felixluser at pnkfx.org
Fri Aug 31 16:12:06 EDT 2007
Dan-
On Aug 31, 2007, at 3:13 PM, Dan Muresan wrote:
> Hi all,
>
> I've recently discovered (and installed) Larceny, and I have a
> couple of basic questions:
>
> 1) Where's the most complete documentation? I see that Larceny
> supports a (require ...) form, but it doesn't seem to be documented
> on the website.
There is an auto-built copy of the user documentation at the
following url:
http://larceny.ccs.neu.edu/doc/
However, the user documentation won't actually help you understand
the require procedure, since we neglected to put documentation for it
in there.
One reason for this neglect is that at the time that we (re)
implemented require, we expected the need for the require procedure
to become obsolete with the shift to R6RS style libraries. You can
see some notes on this at the following page on the Larceny Wiki.
http://larceny.ccs.neu.edu/larceny-trac/wiki/RationalizingLarceny
I am not sure how much effort we will put into documenting the
require procedure, since I am not certain that it will remain an
established part of Larceny.
For the time being, the best ways I can suggest to understand the
behavior of require (or any other feature you cannot find
documentation for) is to ask about it on this list, or to read the
source code for the feature.
In this case, the relevant source code for require is here:
http://larceny.ccs.neu.edu/larceny-trac/browser/trunk/larceny_src/src/
Lib/Common/require.sch
(I normally would not point a user at a source file and expect that
to suffice, but this file is short, reasonably well documented, and
factored into small chunks, so I hope you will forgive me for doing
so in this particular case.)
A three sentence description of the require form:
(require 'lib) searches directories given by the current-require-path
parameter for a Scheme file matching lib and loads the first such
file it finds. Relative paths in the directory list are resolved
with respect to the current-larceny-root parameter. Repeat attempts
to load lib again have no effect.
Here is an example usage:
% larceny
Larceny v0.94 "Doomsday Device" (Aug 14 2007 10:56:17,
precise:Linux:unified)
larceny.heap, built on Wed Aug 1 12:53:28 EDT 2007
> (load-verbose #t) ;; instrument load to track require's behavior
#t
> (apropos 'require) ;; will fail since apropos procedure is not yet
defined
Error: Undefined global variable "apropos".
Entering debugger; type "?" for help.
debug> q
> (require 'apropos) ;; will load apropos library
; Loading /home/pnkfelix/larcenydev/trunk/larceny_src/lib/Standard/
apropos.sch
; Loading /home/pnkfelix/larcenydev/trunk/larceny_src/lib/Base/
string.fasl
; Loading /home/pnkfelix/larcenydev/trunk/larceny_src/lib/Base/
list.fasl#t
> (apropos 'require) ;; now apropos will work
(clear-require-loaded-files!
current-require-path
require)
> (require 'apropos) ;; now no load will occur because apropos is
already loaded
#f
> 2) Most of my Scheme programs (usually developed for SISC and/or
> Chicken) use the popular SRFI's (1, 8, 9, 13, 43, 69 etc)
> extensively; I usually load them with (require-extension (srfi n))
> in the beginning of my programs. What's the easiest way to port to
> Larceny? Should I copy the reference implementations?
I assume that when you refer to require-extension, you are referring
to the special form defined in SRFI-55?
We do not have an implementation of SRFI-55 in the Larceny
distribution. I suspect that the reference implementation would be
an okay stopgap measure, with two caveats:
1. You would still have to write down several invocations of register-
extension somewhere (one for each srfi that you wanted to make
available via SRFI-55). Larceny's require function used to have an
internal table mapping symbols to source files (which would be the
analogous thing to the N invocations of register-extension that I am
imagining), but now searches a set of paths looking for matching
files. So that's one reason that a Larceny-specific implementation
of SRFI-55 that used require might be more appropriate.
2. The reference implementation does not seem to cache whether an
extension has already been required; it will reload each extension
every time require-extension is evaluated (I think). That is a
second reason that a Larceny-specific implementation of SRFI-55 atop
the require procedure might be more appropriate.
A minimal port of require-extension atop Larceny's require might be a
pretty simple syntax-rules macro. Here's a stab at one:
(define-syntax require-extension
(syntax-rules (srfi)
((_ (srfi m n ...))
(for-each
(lambda (i) (require (string-append "srfi-" (number->string i))))
'(m n ...)))))
Depending on one's interpretation of SRFI-55, this may be a fine
implementation of require-extension for Larceny.
-Felix
p.s. (Only if you're interested) there is one feature missing from
the above SRFI-55 implementation that I, as a user, would desire:
expansion of a require-extension form should extend the compile-time
syntactic environment with any syntax that is provided by the SRFI's
that the form is requiring.
I spent some time over a year ago trying to incorporate such a
feature into Larceny's require form; if you're curious about the
issues I encountered, you can go read:
http://larceny.ccs.neu.edu/larceny-trac/wiki/ExtendingRequire
In the end I stopped trying to make this work, in part because I
expected that R6RS library support would obviate the need for such
functionality, and in part because it really was fundamentally
difficult to implement properly.
More information about the Larceny-users
mailing list