[[LibrariesChapter]]

R7RS/R6RS Libraries
-------------------

The R6RS standard added a `library` mechanism for batch programs.
The R7RS standard added a similar `define-library` syntax with
several new features, and allowed libraries to be used within
interactive read/eval/print loops as well as batch programs.

The libraries discussed within this chapter cannot be used in
Larceny's R5RS mode.


Interactive computing
~~~~~~~~~~~~~~~~~~~~~

Larceny's `-r7` command-line option automatically imports the
`(scheme base)` library.  The `-r7r6` command-line option imports
all of the R7RS Red Edition and R6RS standard libraries, including
those deprecated by Larceny.


[[R7rsAutomaticLoadingSection]]

Automatic loading
~~~~~~~~~~~~~~~~~

As an extension to the R7RS and R6RS, Larceny attempts to load
libraries automatically when they are first imported.
Autoloading makes interactive development and
<<CompilingChapter,separate compilation>>
much more convenient.

All of Larceny's
<<R7rsPreDefinedSection,predefined libraries>>
can be autoloaded.

To enable autoloading of other R7RS/R6RS libraries,
including libraries you've written yourself, you can:

- use the <<R7rsLibraryPathSection,`-I` or `-A` command-line options>>
- use the <<R7rsLibraryPathSection,`LARCENY_LIBPATH`>> environment variable
- use <<current-require-path,`current-require-path`>>
- edit `startup.sch` in Larceny's root directory
- add the libraries to Larceny's `lib` directory


[[R7rsDynamicLoadingSection]]

Explicit loading
~~~~~~~~~~~~~~~~

Larceny automatically loads R7RS/R6RS libraries when
they are first imported.  This is usually the most
convenient way to load a library, but autoloading
can't be used to load a top-level program into an
interactive session.  Explicit
loading is needed for top-level programs, for libraries
that don't reside in Larceny's
<<current-require-path,`current-require-path`>>,
and for libraries that are defined in files whose names
do not follow Larceny's
<<NamingChapter,standard naming conventions>>.

In theory, explicit loading is the only portable way for R7RS
programs to load a library.
<<LibraryResolutionSection,
There is no portable way for R6RS programs to load or import libraries>>,
so R6RS programs must rely upon implementation-specific
mechanisms such as Larceny's autoloading.

////////////////////////////////////////////////////////////////
Explicit loading also makes it possible to write portable
programs whose source files conform to both the R5RS and
ERR5RS.  Two different configuration files, one for the
R5RS and one for ERR5RS, can perform all of the imports
and loads needed to run the program.
////////////////////////////////////////////////////////////////

For explicit loading of nonstandard libraries, top-level
programs, or unadorned R5RS-style code from a file, you
must first import a suitable load procedure:

----------------------------------------------------------------
    > (import (scheme load))
----------------------------------------------------------------

Loading a library does not automatically import it.
To use the variables and syntax that are exported by a
library, you must import that library explicitly:

----------------------------------------------------------------
    > (load "lib/R6RS/larceny/benchmarking.sls")
    > (import (larceny benchmarking))
    > (time (vector-for-each + (make-vector 1000000 0)))
    Words allocated: 3053286
    Elapsed time...: 25 ms (User: 25 ms; System: 0 ms)
    Elapsed GC time: 3 ms (CPU: 2 in 2 collections (1 minor).)
----------------------------------------------------------------

In Larceny, you may omit the call to `load` because the
`(larceny benchmarking)` library will be autoloaded when
it is imported.  In other implementations of the R7RS, you
may have to load all of the nonstandard libraries that will
be imported by a top-level program or library before you
load that top-level program or library.

////////////////////////////////////////////////////////////////
You do not have to import those libraries into the R7RS
top level, however, unless you want to use the variables
and syntax exported by those libraries in the expressions
and definitions you evaluate at the top level.
////////////////////////////////////////////////////////////////


[[Err5rsPreDefinedSection]]
[[R7rsPreDefinedSection]]

Predefined libraries
~~~~~~~~~~~~~~~~~~~~

Larceny predefines several nonstandard libraries in addition
to the standard R7RS and R6RS libraries, and autoloads them
for your convenience.  The predefined, autoloadable libraries
include:

Composite library:

    (larceny r7r6)                         ; all R7RS/R6RS standard libraries

link:../r7rs.pdf[R7RS (small)] standard libraries:

    (scheme base)
    (scheme case-lambda)
    (scheme char)
    (scheme complex)
    (scheme cxr)
    (scheme eval)
    (scheme file)
    (scheme inexact)
    (scheme lazy)
    (scheme load)
    (scheme process-context)
    (scheme r5rs)
    (scheme read)
    (scheme repl)
    (scheme time)
    (scheme write)

http://trac.sacrideo.us/wg/wiki/RedEdition[R7RS Red Edition] libraries:

    (scheme box)                           ; SRFI 111
    (scheme charset)                       ; SRFI 14
    (scheme comparator)                    ; SRFI 128
    (scheme ephemeron)                     ; SRFI 124
    (scheme generator)                     ; SRFI 121
    (scheme hash-table)                    ; SRFI 125 (partially deprecated)
    (scheme ideque)                        ; SRFI 134
    (scheme ilist)                         ; SRFI 116
    (scheme list)                          ; SRFI 1
    (scheme list-queue)                    ; SRFI 117
    (scheme lseq)                          ; SRFI 127
    (scheme rlist)                         ; SRFI 101 (systematically renamed)
    (scheme set)                           ; SRFI 113
    (scheme sort)                          ; SRFI 132
    (scheme stream)                        ; SRFI 41
    (scheme text)                          ; SRFI 135
    (scheme vector)                        ; SRFI 133

http://www.r6rs.org/[R6RS] standard libraries:

    (rnrs base (6))                        ; R6RS chapter 9
    (rnrs unicode (6))                     ; R6RS library chapter 1
    (rnrs bytevectors (6))                 ; R6RS library chapter 2
    (rnrs lists (6))                       ; R6RS library chapter 3
    (rnrs sorting (6))                     ; R6RS library chapter 4
    (rnrs control (6))                     ; R6RS library chapter 5
    (rnrs exceptions (6))                  ; R6RS library section 7.1
    (rnrs conditions (6))                  ; R6RS library sections 7.2 and 7.3
    (rnrs io ports (6))                    ; R6RS library sections 8.1 and 8.2
    (rnrs io simple (6))                   ; R6RS library sections 8.1 and 8.3
    (rnrs files (6))                       ; R6RS library chapter 9
    (rnrs programs (6))                    ; R6RS library chapter 10
    (rnrs arithmetic fixnums (6))          ; R6RS library section 11.2
    (rnrs arithmetic flonums (6))          ; R6RS library section 11.3
    (rnrs arithmetic bitwise (6))          ; R6RS library section 11.4
    (rnrs syntax-case (6))                 ; R6RS library chapter 12
    (rnrs hashtables (6))                  ; R6RS library chapter 13
    (rnrs enums)                           ; R6RS library chapter 14
    (rnrs (6))                             ; R6RS library chapter 15
    (rnrs eval (6))                        ; R6RS library chapter 16
    (rnrs mutable-pairs (6))               ; R6RS library chapter 17
    (rnrs mutable-strings (6))             ; R6RS library chapter 18
    (rnrs r5rs (6))                        ; R6RS library chapter 19

R6RS standard libraries that are autoloadable but deprecated in Larceny
because they have been superseded by the R7RS and SRFI 99 record
facilities:

    (rnrs records procedural (6))          ; R6RS library section 6.3
    (rnrs records inspection (6))          ; R6RS library section 6.4
    (rnrs records syntactic (6))           ; R6RS library section 6.2

http://srfi.schemers.org/[SRFI] libraries:

    (srfi 1 lists)                         ; list library
    (srfi 2 and-let*)                      ; extended `and` and `let*`
    (srfi 5 let)                           ; extended version of `let`
    (srfi 6 basic-string-ports)            ; basic string ports
    (srfi 8 receive)                       ; binding to multiple values
    (srfi 9 records)                       ; defining record types
    (srfi 11 let-values)                   ; syntax for multiple values
    (srfi 13 strings)                      ; string libraries
    (srfi 14 char-sets)                    ; character-set library (default)
    (srfi 14 unicode)                      ;   for all Unicode characters
    (srfi 14 bmp)                          ;   for the Basic Multilingual Plane
    (srfi 14 latin-1)                      ;   for ISO 8859-1 (Latin-1)
    (srfi 16 case-lambda)                  ; syntax for variable arity
    (srfi 17 generalized-set!)             ; generalized set!
    (srfi 19 time)                         ; time data types and procedures
    (srfi 23 error)                        ; error reporting mechanism
    (srfi 25 multi-dimensional-arrays)     ; multi-dimensional array primitives
    (srfi 26 cut)                          ; specializing without currying
    (srfi 27 random-bits)                  ; sources of random bits
    (srfi 28 basic-format-strings)         ; basic format strings
    (srfi 29 localization)                 ; localization
    (srfi 31 rec)                          ; `rec` syntax
    (srfi 37)                              ; program argument processor
    (srfi 38 with-shared-structure)        ; i/o for data with shared structure
    (srfi 39 parameters)                   ; parameter objects
    (srfi 41 streams)                      ; streams
    (srfi 42 eager-comprehensions)         ; eager comprehensions
    (srfi 45 lazy)                         ; iterative lazy algorithms
    (srfi 48 intermediate-format-strings)  ; format
    (srfi 51 rest-values)                  ; rest values hackery
    (srfi 54 cat)                          ; still more formatting
    (srfi 59 vicinities)                   ; vicinity
    (srfi 61 cond)                         ; a more general cond clause
    (srfi 63 arrays)                       ; homogeneous, heterogeneous arrays
    (srfi 64 testing)                      ; an API for test suites
    (srfi 67 compare-procedures)           ; three-way comparison procedures
    (srfi 78 lightweight-testing)          ; lightweight testing
    (srfi 87 case)                         ; a more general case clause
    (srfi 98 os-environment-variables)     ; environment variables
    (srfi 99 records)                      ; (composite library)
    (srfi 99 records procedural)           ; (procedural API)
    (srfi 99 records inspection)           ; (inspection API)
    (srfi 99 records syntactic)            ; (syntactic API)
    (srfi 101 random-access-lists)         ; fast and purely functional lists
    (srfi 111 boxes)                       ; boxes
    (srfi 112)                             ; environment inquiry
    (srfi 113 sets)                        ; sets and bags
    (srfi 115 regexp)                      ; regular expressions
    (srfi 116 ilists)                      ; immutable lists
    (srfi 117)                             ; queues based on lists
    (srfi 121)                             ; generators
    (srfi 123)                             ; generic accessor/modifier operators
    (srfi 124)                             ; ephemerons
    (srfi 126)                             ; R6RS-based hashtables
    (srfi 127)                             ; lazy sequences
    (srfi 128)                             ; comparators (reduced)
    (srfi 129)                             ; titlecase procedures
    (srfi 131)                             ; ERR5RS record syntax (reduced)
    (srfi 134)                             ; immutable deques
    (srfi 138)                             ; compiling top-level programs
    (srfi 141)                             ; integer division
    (srfi 143)                             ; fixnums
    (srfi 144)                             ; flonums
    (srfi 145)                             ; assumptions
    (srfi 146)                             ; mappings
    (srfi 151)                             ; bitwise operations
    (srfi 152)                             ; string library (reduced)

[NOTE]
================================================================
For backward compatibility,
`(srfi 1 lists)` through `(srfi 101 random-access-lists)` are also
available with the SRFI 97 naming convention in which the number is
preceded by a colon, as in `(srfi :1 lists)`.
With the more liberal R7RS syntax, that SRFI 97 naming convention
is now unnecessary.
Larceny has extended the R6RS `library` syntax to allow R6RS libraries
to import R7RS libraries that follow the R7RS naming convention shown
in the list above.
================================================================

SRFI libraries that are autoloadable but deprecated in Larceny,
usually because they have been superseded in whole or in part by
R7RS or R6RS or other SRFI libraries or syntax (shown in parentheses):

    (srfi 0)                               ; cond-expand (scheme base)
    (srfi 30)                              ; nested multi-line comments (#| |#)
    (srfi 34)                              ; exception handling (scheme base)
    (srfi 43 vectors)                      ; vector library (scheme vector)
    (srfi 55)                              ; require-extension (import)
    (srfi 60 integer-bits)                 ; (rnrs arithmetic bitwise)
    (srfi 62)                              ; S-expression comments ( #; )
    (srfi 66 octet-vectors)                ; (scheme base)
    (srfi 69 basic-hash-tables)            ; (scheme hash-table), (srfi 126)
    (srfi 71 let)                          ; extensions of let, let*, letrec
    (srfi 74 blobs)                        ; (rnrs bytevectors)
    (srfi 95 sorting-and-merging)          ; (scheme sorting)
    (srfi 114 comparators)                 ; (scheme comparator)
    (srfi 125)                             ; (scheme hash-table)
    (srfi 130)                             ; (scheme text)
    (srfi 132)                             ; (scheme sorting)
    (srfi 133)                             ; (scheme vector)
    (srfi 135)                             ; (scheme text)
    (srfi 136)                             ; record types (srfi 99), (srfi 131)
    (srfi 137)                             ; unique types (srfi 99), (srfi 131)
    (srfi 142)                             ; bitwise operations (srfi 151)
    (srfi 147)                             ; macro transformers (scheme base)

ERR5RS libraries that are autoloadable but deprecated in Larceny
because they have been superseded by the R7RS, SRFI 99, and SRFI 131
record facilities: 

    (err5rs records procedural)            ; ERR5RS records (procedural API)
    (err5rs records inspection)            ; ERR5RS records (inspection API)
    (err5rs records syntactic)             ; ERR5RS records (syntactic API)
    (err5rs load)                          ; ERR5RS load procedure

Other autoloadable libraries:

    (larceny load)                         ; extension of (err5rs load)
    (larceny compiler)                     ; separate compilation (R7RS/R6RS)
    (larceny benchmarking)                 ; timing facilities
    (larceny profiling)                    ; profiling of Scheme code
    (larceny r7r6)                         ; all R7RS/R6RS standard libraries
    (larceny records printer)              ; custom printing of records
    (larceny shivers-syntax)               ; syntax favored by Olin Shivers
    (r5rs)                                 ; approximates the R5RS top level
    (explicit-renaming)                    ; macros with explicit renaming


[[R7rsLibraryPathSection]]

Library path
~~~~~~~~~~~~

Larceny's autoload feature locates R7RS/R6RS libraries
by performing a
<<LibraryTranslationSection, depth-first search>>
of the directories that belong to Larceny's
<<current-require-path,`current-require-path`>>.
Libraries will not be autoloaded unless they are defined
in files whose names follow
<<NamingChapter, Larceny's standard conventions>>.

The
<<current-require-path,`current-require-path`>>
is initialized by the `startup.sch` file in Larceny's root
directory.

<<R7rsLibraryPathSection, Larceny's `-I` and `-A` command-line options>>
adds one or more directories to the directories in the
<<current-require-path,`current-require-path`>>.
The `-I` option specifies directories to be searched before the
standard directories; the `-A` option specifies directories to
be searched after the standard directories.

You can specify those options more than once on the command line.
On most systems, you can also specify multiple directories
by separating them with a colon; under Windows, use a
semicolon as separator instead.  The first directory
listed will be searched first.

The `LARCENY_LIBPATH`
environment variable can also be used to add one or more directories
to the directories in the
<<current-require-path,`current-require-path`>>,
to be searched before the standard directories.
Multiple directories should be specified as with the `-I` option.

[TIP]
================================================================
If you have a set of portable libraries that run under more than
one implementation of the R7RS, and you want to have a special
version of some of those libraries for Larceny, you can put all
your portable versions in one directory and the Larceny-specific
versions in another.  When you run Larceny, use the `-I`
option and specify the Larceny-specific directory first.
================================================================

[NOTE]
================================================================
The `-I` and `-A` options cannot be used by Scheme scripts,
because command-line options are passed along to the Scheme
script without being interpreted by the `scheme-script` processor.
================================================================

[WARNING]
================================================================
We emphasize that these extensions are non-portable.
Other implementations of the R7RS or R6RS may not provide
anything comparable to Larceny's command-line options or
`LARCENY_LIBPATH` environment variable.
Even if they do, their mappings from library names
to file names may be incompatible with Larceny's.
================================================================


////////////////////////////////////////////////////////////////

[[R6rsPreDefinedSection]]

Using libraries with R6RS top-level programs
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

The R6RS standard does not specify any way for a
top-level program to define its own libraries.
Portable R6RS programs are therefore limited to
importing a subset of the R6RS standard libraries.

As an extension to the R6RS, Larceny allows R6RS
top-level programs and Scheme scripts to define
their own libraries and to import any libraries that are
<<R7rsPreDefinedSection,predefined in Larceny's R7RS mode>>.
////////////////////////////////////////////////////////////////


[[DefiningLibrariesSection]]

Defining libraries
~~~~~~~~~~~~~~~~~~

As an extension to the R7RS and R6RS, Larceny allows a top-level
program or Scheme script to define R7RS/R6RS libraries within
the file that contains the top-level program or Scheme
script, before the import form that begins the top-level
program.  These libraries must be arranged so that no
library depends upon libraries that come later in the
file.

[WARNING]
================================================================
We emphasize that this extension is non-portable.
================================================================


[[ERR5RSprimitivesSection]]
[[R7rsPrimitivesSection]]

Importing procedures from Larceny's underlying R5RS system
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

Any of Larceny's R5RS-mode top-level procedures can be imported
into an R7RS or R6RS library or program by using an import
declaration with a `primitives` clause that names the R5RS
procedures to be imported.  For example:

----------------------------------------------------------------
    (import (primitives random current-seconds
                        getenv setenv system
                        current-directory file-modification-time)
            (scheme time))
----------------------------------------------------------------

[WARNING]
================================================================
This feature is highly non-portable.
Other implementations of the R7RS or R6RS may not even
have an underlying implementation of the R5RS.
================================================================

