cs: enable embedding in other applications
The "Inside: Racket C API" manual now has a CS part and a BC part.
This commit is contained in:
parent
d6d30d2fcc
commit
00b6803e36
|
@ -87,13 +87,16 @@ Racket is available in three implementation variants: @deftech{3m},
|
|||
|
||||
]
|
||||
|
||||
The @tech{3m} and @tech{CGC} variants are collectively known as the
|
||||
@deftech{BC} (``before CS'') variant.
|
||||
|
||||
In general, Racket programs should run the same in all variants.
|
||||
Furthermore, the performance characteristics of Racket program should
|
||||
be similar in the @tech{3m} and @tech{CS} variants. The cases where a
|
||||
program may depends on the variant will typically involve interactions
|
||||
with foreign libraries; in particular, the Racket C API described in
|
||||
@other-doc[inside-doc] is available only for the virtual machine of
|
||||
the @tech{3m} and @tech{CGC} variants.
|
||||
@other-doc[inside-doc] is different for the @tech{3m} and @tech{CGC}
|
||||
variants versus the @tech{CS} variant.
|
||||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
|
|
30
pkgs/racket-doc/scribblings/inside/bc.scrbl
Normal file
30
pkgs/racket-doc/scribblings/inside/bc.scrbl
Normal file
|
@ -0,0 +1,30 @@
|
|||
#lang scribble/base
|
||||
|
||||
@title[#:style '(toc grouper) #:tag "bc"]{Inside Racket BC (3m and CGC)}
|
||||
|
||||
The Racket BC API was originally designed for a tight integration with
|
||||
C code. As a result, the BC API is considerably larger than the Racket
|
||||
CS API.
|
||||
|
||||
@local-table-of-contents[]
|
||||
|
||||
@include-section["overview.scrbl"]
|
||||
@include-section["embedding.scrbl"]
|
||||
@include-section["extensions.scrbl"]
|
||||
@include-section["values.scrbl"]
|
||||
@include-section["memory.scrbl"]
|
||||
@include-section["namespaces.scrbl"]
|
||||
@include-section["procedures.scrbl"]
|
||||
@include-section["eval.scrbl"]
|
||||
@include-section["exns.scrbl"]
|
||||
@include-section["threads.scrbl"]
|
||||
@include-section["params.scrbl"]
|
||||
@include-section["contmarks.scrbl"]
|
||||
@include-section["strings.scrbl"]
|
||||
@include-section["numbers.scrbl"]
|
||||
@include-section["ports.scrbl"]
|
||||
@include-section["structures.scrbl"]
|
||||
@include-section["security.scrbl"]
|
||||
@include-section["custodians.scrbl"]
|
||||
@include-section["subprocesses.scrbl"]
|
||||
@include-section["misc.scrbl"]
|
254
pkgs/racket-doc/scribblings/inside/cs-embedding.scrbl
Normal file
254
pkgs/racket-doc/scribblings/inside/cs-embedding.scrbl
Normal file
|
@ -0,0 +1,254 @@
|
|||
#lang scribble/doc
|
||||
@(require "utils.rkt"
|
||||
scribble/bnf)
|
||||
|
||||
@title[#:tag "cs-embedding"]{Embedding into a Program}
|
||||
|
||||
@section-index["embedding Racket CS"]
|
||||
|
||||
To embed Racket CS in a program, follow these steps:
|
||||
|
||||
@itemize[
|
||||
|
||||
@item{Locate or build the Racket CS library.
|
||||
|
||||
On Unix, the library is @as-index{@filepath{libracketcs.a}}.
|
||||
Building from source and installing places the libraries into the
|
||||
installation's @filepath{lib} directory.
|
||||
|
||||
On Windows, link to @filepath{libracketcs@italic{x}.dll} (where
|
||||
@italic{x} represents the version number). At run time, either
|
||||
@filepath{libracketcs@italic{x}.dll} must be moved to a location in
|
||||
the standard DLL search path, or your embedding application must
|
||||
``delayload'' link the DLLs and explicitly load them before use.
|
||||
(@filepath{Racket.exe} uses the latter strategy.)
|
||||
|
||||
On Mac OS, besides @as-index{@filepath{libracketcs.a}} for static
|
||||
linking, a dynamic library is provided by the @filepath{Racket}
|
||||
framework, which is typically installed in @filepath{lib}
|
||||
sub-directory of the installation. Supply @exec{-framework Racket}
|
||||
to @exec{gcc} when linking, along with @exec{-F} and a path to the
|
||||
@filepath{lib} directory. At run time, either
|
||||
@filepath{Racket.framework} must be moved to a location in the
|
||||
standard framework search path, or your embedding executable must
|
||||
provide a specific path to the framework (possibly an
|
||||
executable-relative path using the Mach-O @tt["@executable_path"]
|
||||
prefix).}
|
||||
|
||||
@item{For each C file that uses Racket library functions,
|
||||
@cpp{#include} the files @as-index{@filepath{chezscheme.h}}
|
||||
and @as-index{@filepath{racketcs.h}}.
|
||||
|
||||
The @filepath{chezscheme.h} and @filepath{racketcs.h} files are
|
||||
distributed with the Racket software in the installation's
|
||||
@filepath{include} directory. Building and installing from source
|
||||
also places this file in the installation's @filepath{include}
|
||||
directory.}
|
||||
|
||||
@item{In your program, call @cppi{racket_boot}. The
|
||||
@cppi{racket_boot} function takes a pointer to a
|
||||
@cpp{racket_boot_arguments_t} for configuring the Racket instance.
|
||||
After zeroing out the @cpp{racket_boot_arguments_t} value
|
||||
(typicially with @cpp{memset}), only the following fields are
|
||||
required to be set:
|
||||
|
||||
@itemlist[
|
||||
|
||||
@item{@cpp{exec_file} --- a path to be reported by
|
||||
@racket[(find-system-path 'exec-file)], usually
|
||||
@cpp{argv[0]} for the @cpp{argv} received by your program's
|
||||
@cpp{main}.}
|
||||
|
||||
@item{@cpp{boot1_path} --- a path to @filepath{petite.boot}. Use
|
||||
a path that includes at least one directory separator.}
|
||||
|
||||
@item{@cpp{boot2_path} --- a path to @filepath{scheme.boot} (with
|
||||
a separator).}
|
||||
|
||||
@item{@cpp{boot3_path} --- a path to @filepath{racket.boot}
|
||||
(which a separator).}
|
||||
|
||||
]
|
||||
|
||||
The @filepath{petite.boot}, @filepath{scheme.boot}, and
|
||||
@filepath{racket.boot} files are distributed with the Racket
|
||||
software in the installation's @filepath{lib} directory. These files
|
||||
can be combined into a single file---or even embedded into the
|
||||
executable---as long as the @cpp{boot1_offset}, @cpp{boot2_offset},
|
||||
and @cpp{boot3_offset} fields of @cpp{racket_boot_arguments_t} are
|
||||
set to identify the starting offset of each boot image in the file.}
|
||||
|
||||
@item{Configure the main thread's namespace by adding module
|
||||
declarations. The initial namespace contains declarations only for a
|
||||
few primitive modules, such as @racket['#%kernel], and no bindings
|
||||
are imported into the top-level environment.
|
||||
|
||||
To embed a module like @racketmodname[racket/base] (along with all
|
||||
its dependencies), use
|
||||
@seclink["c-mods" #:doc raco-doc]{@exec{raco ctool --c-mods @nonterm{dest}}},
|
||||
which generates a C file @nonterm{dest}
|
||||
that contains modules in bytecode form as encapsulated in a static
|
||||
array. The generated C file defines a @cppi{declare_modules}
|
||||
function that takes no arguments and installs the modules into
|
||||
the environment, and it adjusts the module name resolver to access the
|
||||
embedded declarations. If embedded modules refer to runtime files
|
||||
that need to be carried along, supply @DFlag{runtime} to
|
||||
@exec{raco ctool --c-mods} to collect the runtime files into a
|
||||
directory; see @secref[#:doc raco-doc "c-mods"] for more information.
|
||||
|
||||
Alternatively, set fields like @cpp{collects_dir}, @cpp{config_dir},
|
||||
and/or @cpp{argv} in the @cpp{racket_boot_arguments_t} passed to
|
||||
@cppi{scheme_boot} to locate collections/packages and initialize the
|
||||
namespace the same way as when running the @exec{racket} executable.
|
||||
|
||||
On Windows, @exec{raco ctool --c-mods @nonterm{dest} --runtime
|
||||
@nonterm{dest-dir}} includes in @nonterm{dest-dir} optional DLLs
|
||||
that are referenced by the Racket library to support
|
||||
@racket[bytes-open-converter]. Set @cpp{dll_dir} in
|
||||
@cpp{racket_boot_arguments_t} to register @nonterm{dest-dir} so that
|
||||
those DLLs can be found at run time.}
|
||||
|
||||
@item{Access Racket through @cppi{racket_dynamic_require},
|
||||
@cppi{racket_eval}, and/or other functions described in this manual.
|
||||
|
||||
If the embedding program configures built-in parameters in a way
|
||||
that should be considered part of the default configuration, then
|
||||
call the @racketidfont{seal} function provided by the primitive
|
||||
@racketidfont{#%boot} module afterward. The snapshot of parameter
|
||||
values taken by @cpp{scheme_seal_parameters} is used for certain
|
||||
privileged operations, such as installing a @|PLaneT| package.}
|
||||
|
||||
@item{Compile the program and link it with the Racket libraries.}
|
||||
|
||||
]
|
||||
|
||||
@index['("allocation")]{Racket} values may be moved or garbage
|
||||
collected any time that @cpp{racket_...} functions are used to run
|
||||
Racket code. Do not retain a reference to any Racket value across such
|
||||
a call.
|
||||
|
||||
For example, the following is a simple embedding program that runs a
|
||||
module @filepath{run.rkt}, assuming that @filepath{run.c} is created
|
||||
as
|
||||
|
||||
@commandline{raco ctool --c-mods run.c "run.rkt"}
|
||||
|
||||
to generate @filepath{run.c}, which encapsulates the compiled form of
|
||||
@filepath{run.rkt} and all of its transitive imports (so that they
|
||||
need not be found separately a run time). Copies of
|
||||
@filepath{petite.boot}, @filepath{scheme.boot}, and
|
||||
@filepath{racket.boot} must be in the current directory on startup.
|
||||
|
||||
@filebox["main.c"]{
|
||||
@verbatim[#:indent 2]{
|
||||
#include <string.h>
|
||||
#include "chezscheme.h"
|
||||
#include "racketcs.h"
|
||||
|
||||
#include "run.c"
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
racket_boot_arguments_t ba;
|
||||
|
||||
memset(&ba, 0, sizeof(ba));
|
||||
|
||||
ba.boot1_path = "./petite.boot";
|
||||
ba.boot2_path = "./scheme.boot";
|
||||
ba.boot3_path = "./racket.boot";
|
||||
|
||||
ba.exec_file = argv[0];
|
||||
|
||||
racket_boot(&ba);
|
||||
|
||||
declare_modules();
|
||||
|
||||
ptr mod = Scons(Sstring_to_symbol("quote"),
|
||||
Scons(Sstring_to_symbol("run"),
|
||||
Snil));
|
||||
|
||||
racket_dynamic_require(mod, Sfalse);
|
||||
|
||||
return 0;
|
||||
}
|
||||
}}
|
||||
|
||||
As another example, the following is a simple embedding program that
|
||||
evaluates all expressions provided on the command line and displays
|
||||
the results, then runs a @racket[read]-@racket[eval]-@racket[print]
|
||||
loop, all using @racketmodname[racket/base]. Run
|
||||
|
||||
@commandline{raco ctool --c-mods base.c ++lib racket/base}
|
||||
|
||||
to generate @filepath{base.c}, which encapsulates @racket[racket/base]
|
||||
and all of its transitive imports.
|
||||
|
||||
@filebox["main.c"]{
|
||||
@verbatim[#:indent 2]{
|
||||
#include <string.h>
|
||||
#include "chezscheme.h"
|
||||
#include "racketcs.h"
|
||||
|
||||
#include "base.c"
|
||||
|
||||
static ptr to_bytevector(char *s);
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
racket_boot_arguments_t ba;
|
||||
|
||||
memset(&ba, 0, sizeof(ba));
|
||||
|
||||
ba.boot1_path = "./petite.boot";
|
||||
ba.boot2_path = "./scheme.boot";
|
||||
ba.boot3_path = "./racket.boot";
|
||||
|
||||
ba.exec_file = argv[0];
|
||||
|
||||
racket_boot(&ba);
|
||||
|
||||
declare_modules();
|
||||
|
||||
racket_namespace_require(Sstring_to_symbol("racket/base"));
|
||||
|
||||
{
|
||||
int i;
|
||||
for (i = 1; i < argc; i++) {
|
||||
ptr e = to_bytevector(argv[i]);
|
||||
e = Scons(Sstring_to_symbol("open-input-bytes"),
|
||||
Scons(e, Snil));
|
||||
e = Scons(Sstring_to_symbol("read"), Scons(e, Snil));
|
||||
e = Scons(Sstring_to_symbol("eval"), Scons(e, Snil));
|
||||
e = Scons(Sstring_to_symbol("println"), Scons(e, Snil));
|
||||
|
||||
racket_eval(e);
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
ptr rbase_sym = Sstring_to_symbol("racket/base");
|
||||
ptr repl_sym = Sstring_to_symbol("read-eval-print-loop");
|
||||
|
||||
racket_apply(Scar(racket_dynamic_require(rbase_sym,
|
||||
repl_sym)),
|
||||
Snil);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static ptr to_bytevector(char *s)
|
||||
{
|
||||
iptr len = strlen(s);
|
||||
ptr bv = Smake_bytevector(len, 0);
|
||||
memcpy(Sbytevector_data(bv), s, len);
|
||||
return bv;
|
||||
}
|
||||
}}
|
||||
|
||||
If modules embedded in the executable need to access runtime files
|
||||
(via @racketmodname[racket/runtime-path] forms), supply the
|
||||
@DFlag{runtime} flag to @seclink["ctool" #:doc raco-doc]{@exec{raco ctool}}, specifying a directory
|
||||
where the runtime files are to be gathered. The modules in the
|
||||
generated @filepath{.c} file will then refer to the files in that
|
||||
directory.
|
40
pkgs/racket-doc/scribblings/inside/cs-eval.scrbl
Normal file
40
pkgs/racket-doc/scribblings/inside/cs-eval.scrbl
Normal file
|
@ -0,0 +1,40 @@
|
|||
#lang scribble/doc
|
||||
@(require "utils.rkt"
|
||||
(for-label ffi/unsafe/vm))
|
||||
|
||||
@title[#:tag "cs-eval"]{Evaluation and Running Modules}
|
||||
|
||||
The @cppi{racket_apply} function provides basic evaluation support,
|
||||
but @cppi{racket_eval}, @cppi{racket_dynamic_require}, and
|
||||
@cppi{racket_namespace_require} provide higher-level support for the
|
||||
most common evaluation tasks.
|
||||
|
||||
@function[(ptr racket_eval [ptr s_expr])]{
|
||||
|
||||
Evaluates @var{s_expr} in the initial Racket thread using its current
|
||||
@tech[#:doc reference-doc]{namespace}, the same as calling
|
||||
@racket[eval]. The @var{s_expr} can be an S-expression constructed
|
||||
with pairs, symbols, etc., or it can be a @tech[#:doc
|
||||
reference-doc]{syntax object}.
|
||||
|
||||
Use @cppi{racket_namespace_require} to initialize a namespace, or use
|
||||
@cppi{racket_dynamic_require} to access functionality without going
|
||||
through a top-level namespace. Although those functions are the same
|
||||
as using @racket[namespace-require] and @racket[dynamic-require], they
|
||||
work without having those identifiers bound in a namespace already.}
|
||||
|
||||
@function[(ptr racket_dynamic_require [ptr module_path] [ptr sym_or_false])]{
|
||||
|
||||
The same as calling @racket[dynamic-require] in the initial Racket
|
||||
thread using its current namespace. See also @cppi{racket_eval}.}
|
||||
|
||||
|
||||
@function[(ptr racket_namespace_require [ptr module_path])]{
|
||||
|
||||
The same as calling @racket[namespace-require] in the initial Racket
|
||||
thread using its current namespace. See also @cppi{racket_eval}.}
|
||||
|
||||
@function[(ptr racket_primitive [const-char* name])]{
|
||||
|
||||
Accesses a primitive function in the same sense as
|
||||
@racket[vm-primitive] from @racketmodname[ffi/unsafe/vm].}
|
96
pkgs/racket-doc/scribblings/inside/cs-overview.scrbl
Normal file
96
pkgs/racket-doc/scribblings/inside/cs-overview.scrbl
Normal file
|
@ -0,0 +1,96 @@
|
|||
#lang scribble/doc
|
||||
@(require "utils.rkt")
|
||||
|
||||
@title[#:tag "cs-overview"]{Overview}
|
||||
|
||||
The Racket CS run-time system is implemented by a wrapper around the
|
||||
Chez Scheme kernel. The wrapper implements additional glue to the
|
||||
operating system (e.g., for I/O and networking) and provides entry
|
||||
points into the Racket layer's evaluator.
|
||||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section{``S'' versus ``Racket''}
|
||||
|
||||
In the C API for Racket CS, names that start with @cpp{S} are from the
|
||||
Chez Scheme layer, while names that start with @cpp{racket_} are from
|
||||
the Racket wrapper.
|
||||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section{Building Racket CS from Source}
|
||||
|
||||
The normal Racket distribution includes @filepath{.rkt} sources for
|
||||
collection-based libraries. After modifying library files, run
|
||||
@exec{raco setup} (see @secref[#:doc '(lib
|
||||
"scribblings/raco/raco.scrbl") "setup"]) to rebuild installed
|
||||
libraries.
|
||||
|
||||
The normal Racket distribution does not include the C sources for
|
||||
Racket's run-time system. To build Racket from scratch, download a
|
||||
source distribution from @url{http://download.racket-lang.org};
|
||||
detailed build instructions are in the @filepath{README} file in the
|
||||
top-level @filepath{src} directory. You can also get the latest
|
||||
sources from the @tt{git} repository at
|
||||
@url{https://github.com/racket/racket}, but beware that the repository is
|
||||
one step away from a normal source distribution, and it provides build
|
||||
modes that are more suitable for developing Racket itself; see
|
||||
@filepath{INSTALL.txt} in the @tt{git} repository for more
|
||||
information.
|
||||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section[#:tag "cs-memory"]{Racket CS Memory Management}
|
||||
|
||||
@index['("allocation")]{Racket} values may be moved or garbage
|
||||
collected any time that @cpp{racket_...} functions are used to run
|
||||
Racket code. Do not retain a reference to any Racket value across such
|
||||
a call. This requirement contrasts with the 3m and CGC variants of
|
||||
Racket, which provide a way for C code to more directly cooperate with
|
||||
the memory manager.
|
||||
|
||||
API functions that start with @cpp{S} do not collect or move objects
|
||||
unless noted otherwise, so references to Racket values across such
|
||||
calls is safe.
|
||||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section[#:tag "cs-places"]{Racket CS and Places}
|
||||
|
||||
Each Racket @|tech-place| corresponds to a Chez Scheme thread, which
|
||||
also corresponds to an OS-implemented thread. Chez Scheme threads
|
||||
share a global allocation space, so GC-managed objects can be safely
|
||||
be communicated from one place to another. Beware, however, that Chez
|
||||
Scheme threads are unsafe; any synchronization needed to safely share
|
||||
a value across places is must be implemented explicitly. Racket-level
|
||||
functions for places will only share values across places when they
|
||||
can be safely used in both places.
|
||||
|
||||
In an @seclink["cs-embedding"]{embedding application}, the OS thread
|
||||
that originally calls @cpp{racket_boot} is the OS thread of the
|
||||
original place.
|
||||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section{Racket CS and Threads}
|
||||
|
||||
Racket implements threads for Racket programs without aid from the
|
||||
operating system or Chez Scheme's threads, so that Racket threads are
|
||||
cooperative from the perspective of C code. Stand-alone Racket uses a
|
||||
few private OS-implemented threads for background tasks, but these
|
||||
OS-implemented threads are never exposed by the Racket API.
|
||||
|
||||
Racket can co-exist with additional OS-implemented threads, but care
|
||||
must be taken when calling @cpp{S} functions, and additional OS or
|
||||
Chez Scheme threads must not call any @cpp{racket_} function. For
|
||||
other OS threads to call @cpp{S} functions, the thread must be first
|
||||
activated as a Chez Scheme thread using @cppi{Sactivate_thread}.
|
||||
|
||||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section[#:tag "cs-intsize"]{Racket CS Integers}
|
||||
|
||||
The C type @cpp{iptr} is defined by Racket CS headers to be an integer
|
||||
type that is big enough to hold a pointer value. In other words, it is
|
||||
an alias for @cpp{intptr_t}. The @cpp{uptr} type is the unsigned variant.
|
60
pkgs/racket-doc/scribblings/inside/cs-procs.scrbl
Normal file
60
pkgs/racket-doc/scribblings/inside/cs-procs.scrbl
Normal file
|
@ -0,0 +1,60 @@
|
|||
#lang scribble/doc
|
||||
@(require "utils.rkt")
|
||||
|
||||
@title[#:tag "cs-procs"]{Calling Procedures}
|
||||
|
||||
Normally, C programs should call Racket procedures by using
|
||||
@cppi{racket_apply}, which calls the procedure in the initial Racket
|
||||
thread of the main Racket place. Chez Scheme entry points such as
|
||||
@cppi{Scall0} and @cppi{Scall} directly call a procedure outside of
|
||||
any Racket thread, which will not work correctly with Racket
|
||||
facilities such as threads, parameters, continuations, or continuation
|
||||
marks.
|
||||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@function[(ptr racket_apply [ptr proc] [ptr arg_list])]{
|
||||
|
||||
Applies the Racket procedure @var{proc} to the list of arguments
|
||||
@var{arg_list}. The procedure is called in the original Racket thread
|
||||
of the main Racket place. Applying @var{proc} must not raise an
|
||||
exception or otherwise escape from the call to @var{proc}.
|
||||
|
||||
The result is a list of result values, where a single result from
|
||||
@var{proc} causes @cpp{racket_apply} to return a list of length one.
|
||||
|
||||
Other Racket threads can run during the call to @var{proc}. At the
|
||||
point that @var{proc} results, all Racket thread scheduling in the
|
||||
main Racket place is suspended. No garbage collections will occur, so
|
||||
other Racket places can block waiting for garbage collection.}
|
||||
|
||||
@together[(
|
||||
@function[(ptr Scall0 [ptr proc])]
|
||||
@function[(ptr Scall1 [ptr proc] [ptr arg1])]
|
||||
@function[(ptr Scall2 [ptr proc] [ptr arg1] [ptr arg2])]
|
||||
@function[(ptr Scall3 [ptr proc] [ptr arg1] [ptr arg2] [ptr arg3])]
|
||||
)]{
|
||||
|
||||
Applies the Chez Scheme procedure @var{proc} to zero, one, two, or
|
||||
three arguments. Beware that not all Racket procedures are Chez Scheme
|
||||
procedures. (For example, an instance of a structure type that has
|
||||
@racket[prop:procedure] is not a Chez Scheme procedure.)
|
||||
|
||||
The procedure is called outside of any Racket thread, and other Racket
|
||||
threads are not scheduled during the call to @var{proc}. A garbage
|
||||
collection may occur.}
|
||||
|
||||
@together[(
|
||||
@function[(void Sinitframe [iptr num_args])]
|
||||
@function[(void Sput_arg [iptr i] [ptr arg])]
|
||||
@function[(ptr Scall [ptr proc] [iptr num_args])]
|
||||
)]{
|
||||
|
||||
Similar to @cppi{Scall0}, but these functions are used in sequence to
|
||||
apply a Chez Scheme procedure to an arbitrary number of arguments.
|
||||
First, @cppi{Sinitframe} is called with the number of arguments. Then,
|
||||
each argument is installed with @cppi{Sput_arg}, where the @var{i}
|
||||
argument indicates the argumenrt position and @var{arg} is the
|
||||
argument value. Finally, @cppi{Scall} is called with the procedure and
|
||||
the number of arguments (which must match the number provided to
|
||||
@cppi{Sinitframe}).}
|
116
pkgs/racket-doc/scribblings/inside/cs-start.scrbl
Normal file
116
pkgs/racket-doc/scribblings/inside/cs-start.scrbl
Normal file
|
@ -0,0 +1,116 @@
|
|||
#lang scribble/doc
|
||||
@(require "utils.rkt")
|
||||
|
||||
@title[#:tag "cs-start"]{Starting and Declaring Initial Modules}
|
||||
|
||||
As sketched in @secref["cs-embedding"], and embedded instance of
|
||||
Racket CS is started with @cppi{racket_boot}. Functions such as
|
||||
@cppi{racket_embedded_load_bytes} help to initialize a Racket
|
||||
namespace with already-compiled modules.
|
||||
|
||||
For functions and struct fields that contain a path in @cpp{char*}
|
||||
form, the path is treated as UTF-8 encoded on Windows.
|
||||
|
||||
@section[#:tag "cs-boot-arguments"]{Boot and Configuration}
|
||||
|
||||
@function[(void racket_boot [racket_boot_arguments_t* boot_args])]{
|
||||
|
||||
Initializes a Racket CS instance. A main thread is created and then
|
||||
suspended, waiting for further evaluation via @cppi{racket_apply},
|
||||
@cppi{racket_eval}, and similar functions.
|
||||
|
||||
A @cpp{racket_boot_arguments_t} struct contains fields to specify how
|
||||
@cppi{racket_boot} should initialize a Racket instance. New fields may
|
||||
be added in the future, but in that case, a @cpp{0} or @cpp{NULL}
|
||||
value for a field will imply backward-compatible default.
|
||||
|
||||
Fields in @cppdef{racket_boot_arguments_t}:
|
||||
|
||||
@itemlist[
|
||||
|
||||
@item{@cpp{const char *} @cppdef{boot1_path} --- a path to a file
|
||||
containing a Chez Scheme image file with base functionality.
|
||||
Normally, the file is called @filepath{petite.boot}. The path
|
||||
should contain a directory separator, otherwise Chez Scheme
|
||||
will consult its own search path.}
|
||||
|
||||
@item{@cpp{long} @cppdef{boot1_offset} --- an offset into
|
||||
@cpp{boot1_path} to read for the first boot image, which allows
|
||||
boot images to be combined with other data in a single file.
|
||||
The image as distributed is self-terminating, so no size or
|
||||
ending offset is needed.}
|
||||
|
||||
@item{@cpp{const char *} @cppdef{boot2_path} --- like
|
||||
@cpp{boot1_path}, but for the image that contains compiler
|
||||
functionality, normally called @filepath{scheme.boot}.}
|
||||
|
||||
@item{@cpp{long} @cppdef{boot2_offset} --- an offset into
|
||||
@cpp{boot2_path} to read for the second boot image.}
|
||||
|
||||
@item{@cpp{const char *} @cppdef{boot3_path} --- like
|
||||
@cpp{boot1_path}, but for the image that contains Racket
|
||||
functionality, normally called @filepath{racket.boot}.}
|
||||
|
||||
@item{@cpp{long} @cppdef{boot3_offset} --- an offset into
|
||||
@cpp{boot2_path} to read for the thirf boot image.}
|
||||
|
||||
@item{@cpp{int} @cpp{argc} and @cpp{char **} @cpp{argv} ---
|
||||
command-line arguments to be processed the same as for a
|
||||
stand-alone @exec{racket} invocation. If @var{argv} is
|
||||
@cpp{NULL}, the command line @exec{-n} is used, which loads
|
||||
boot files without taking any further action.}
|
||||
|
||||
@item{@cpp{const char *} @cppdef{exec_file} --- a path to use for
|
||||
@racket[(system-type 'exec-file)], usually @cpp{argv[0]} using
|
||||
the @cpp{argv} delivered to a program's @cpp{main}. This
|
||||
field must not be @cpp{NULL}.}
|
||||
|
||||
@item{@cpp{const char *} @cppdef{run_file} --- a path to use for
|
||||
@racket[(system-type 'run-file)]. If the field is @cpp{NULL},
|
||||
the value of @cppi{exec_file} is used.}
|
||||
|
||||
@item{@cpp{const char *} @cppdef{collects_dir} --- a path to use as
|
||||
the main @filepath{collects} directory for locating library
|
||||
collections. If this field holds @cpp{NULL} or @cpp{""}, then
|
||||
the library-collection search path is initialized as empty.}
|
||||
|
||||
@item{@cpp{const char *} @cppdef{config_dir} --- a path to used as an
|
||||
@filepath{etc} directory that holds configuration information,
|
||||
including information about installed packages. If the value if
|
||||
@cpp{NULL}, @cpp{"etc"} is used.}
|
||||
|
||||
@item{@cpp{wchar_t *} @cppdef{dll_dir} --- a path used to find DLLs,
|
||||
such as @exec{iconv} support. Note that this path uses wide
|
||||
characters, not a UTF-8 byte encoding.}
|
||||
|
||||
@item{@cpp{int} @cppdef{cs_compiled_subdir} --- A true value indicates
|
||||
that the @racket[use-compiled-file-paths] parameter should be
|
||||
initialized to have a platform-specific subdirectory of
|
||||
@filepath{compiled}, which is used for a Racket CS installation
|
||||
that overlays a Racket BC installation.}
|
||||
|
||||
]}
|
||||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section[#:tag "cs-embedded-load"]{Loading Racket Modules}
|
||||
|
||||
@together[(
|
||||
@function[(void racket_embedded_load_bytes [const-char* code] [uptr len] [int as_predefined])]
|
||||
@function[(void racket_embedded_load_file [const-char* path] [int as_predefined])]
|
||||
@function[(void racket_embedded_load_file_region [const-char* path] [uptr start] [uptr end] [int as_predefined])]
|
||||
)]{
|
||||
|
||||
These functions evaluate Racket code, either in memory as @var{code}
|
||||
or loaded from @var{path}, in the initial Racket thread. The intent is
|
||||
that the code is already compiled. Normally, also, the contains module
|
||||
declarations. The @seclink["c-mods" #:doc raco-doc]{@exec{raco ctool
|
||||
--c-mods}} and @seclink["c-mods" #:doc raco-doc]{@exec{raco ctool
|
||||
--mods}} commands generate code suitable for loading with these
|
||||
functions, and @DFlag{c-mods} mode generates C code that calls
|
||||
@cppi{racket_embedded_load_bytes}.
|
||||
|
||||
If @var{as_predefined} is true, then the code is loaded during the
|
||||
creation of any new Racket @tech[#:doc reference-doc]{place} in the
|
||||
new place, so that modules declared by the code are loaded in the new
|
||||
place, too.}
|
34
pkgs/racket-doc/scribblings/inside/cs-thread.scrbl
Normal file
34
pkgs/racket-doc/scribblings/inside/cs-thread.scrbl
Normal file
|
@ -0,0 +1,34 @@
|
|||
#lang scribble/doc
|
||||
@(require "utils.rkt")
|
||||
|
||||
@title[#:tag "cs-thread"]{Managing OS-Level Threads}
|
||||
|
||||
Chez Scheme functionality can only be accessed from OS-level threads
|
||||
that are known to the Chez Scheme runtime system. Otherwise, there's a
|
||||
race condition between such an access and a garbage collection that is
|
||||
triggered by other threads.
|
||||
|
||||
A thread not created by Chez Scheme can be made known to the runtime
|
||||
system by activating it with @cppi{Sactivate_thread}. As long as a
|
||||
thread is active by not running Chez Scheme code, the thread prevents
|
||||
garbage collection in all other running threads. Deactivate a thread
|
||||
using @cppi{Sdeactivate_thread}. When a deactivated thread
|
||||
|
||||
@function[(int Sactivate_thread)]{
|
||||
|
||||
Activates the current OS-level thread. An already-activated thread can
|
||||
be activated again, but each activating must be balanced by a
|
||||
decativation. The result is @cpp{0} if the thread was previously
|
||||
activated @cpp{1} otherwise.}
|
||||
|
||||
@function[(void Sdeactivate_thread)]{
|
||||
|
||||
Deactivates the current OS-level thread---or, at least, balances on
|
||||
activation, making the thread deactive if there are no remaining
|
||||
activations to balance with deactivation.}
|
||||
|
||||
@function[(int Sdestroy_thread)]{
|
||||
|
||||
Releases any Chez Scheme resources associated with the current OS
|
||||
thread, which must have been previously activated by which must not be
|
||||
activated still.}
|
266
pkgs/racket-doc/scribblings/inside/cs-values.scrbl
Normal file
266
pkgs/racket-doc/scribblings/inside/cs-values.scrbl
Normal file
|
@ -0,0 +1,266 @@
|
|||
#lang scribble/doc
|
||||
@(require "utils.rkt")
|
||||
|
||||
@title[#:tag "cs-values+types"]{Values and Types}
|
||||
|
||||
A Racket value is represented by a pointer-sized value. The low bits
|
||||
of the value indicate the encoding that it uses. For example, two (on
|
||||
32-bit platform) or three (on 64-bit platforms) low bits indicates a
|
||||
fixnum encoding, while a one low bit and zero second-lowest bit
|
||||
indicates a pair whose address in memory is specified by the other
|
||||
bits.
|
||||
|
||||
The C type for a Racket value is @tt{ptr}. For most Racket types, a
|
||||
constructor is provided for creating values of the type. For example,
|
||||
@cpp{Scons} takes two @cpp{ptr} values and returns the @racket[cons]
|
||||
of the values as a new @cpp{ptr} value. In addition to providing
|
||||
constructors, Racket defines several global constant Racket values,
|
||||
such as @cppi{Strue} for @racket[#t].
|
||||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section[#:tag "cs-constants"]{Global Constants}
|
||||
|
||||
There are six global constants:
|
||||
|
||||
@itemize[
|
||||
|
||||
@item{@cppdef{Strue} --- @racket[#t]}
|
||||
|
||||
@item{@cppdef{Sfalse} --- @racket[#f]}
|
||||
|
||||
@item{@cppdef{Snil} --- @racket[null]}
|
||||
|
||||
@item{@cppdef{Seof-object} --- @racket[eof-object]}
|
||||
|
||||
@item{@cppdef{Svoid} --- @racket[(void)]}
|
||||
|
||||
]
|
||||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section[#:tag "cs-value-funcs"]{Value Functions}
|
||||
|
||||
Many of these functions are actually macros.
|
||||
|
||||
@(define-syntax-rule (predicates (name ...) desc ...)
|
||||
(together
|
||||
(@function[(int name [ptr v])] ...)
|
||||
desc ...))
|
||||
|
||||
@predicates[(Sfixnump
|
||||
Scharp
|
||||
Snullp
|
||||
Seof_objectp
|
||||
Sbooleanp
|
||||
Spairp
|
||||
Ssymbolp
|
||||
Sprocedurep
|
||||
Sflonump
|
||||
Svectorp
|
||||
Sfxvectorp
|
||||
Sbytevectorp
|
||||
Sstringp
|
||||
Sbignump
|
||||
Sboxp
|
||||
Sinexactnump
|
||||
Sexactnump
|
||||
Sratnump
|
||||
Srecordp)]{
|
||||
|
||||
Predicates to recognize different kinds of Racket values, such as
|
||||
fixnums, characters, the empty list, etc. The @cpp{Srecord} predicate
|
||||
recognizes structures, but some built-in Racket datatypes are also
|
||||
implemented as records.}
|
||||
|
||||
@function[(ptr Sfixnum [int i])]{
|
||||
|
||||
Returns a Racket integer value, where @var{i} must fit in a fixnum.}
|
||||
|
||||
@together[(
|
||||
@function[(ptr Sinteger [iptr i])]
|
||||
@function[(ptr Sunsigned [uptr i])]
|
||||
@function[(ptr Sinteger32 [int i])]
|
||||
@function[(ptr Sunsigned32 [unsigned-int i])]
|
||||
@function[(ptr Sinteger64 [long i])]
|
||||
@function[(ptr Sunsigned64 [unsigned-long i])]
|
||||
)]{
|
||||
|
||||
Returns an integer value for different conversions from C, where the
|
||||
result is allocated as a bignum if necessary to hold the value.}
|
||||
|
||||
@function[(iptr Sfixnum_value [ptr v])]{
|
||||
|
||||
Converts a Racket fixnum to a C integer.}
|
||||
|
||||
@together[(
|
||||
@function[(iptr Sinteger_value [ptr v])]
|
||||
@function[(uptr Sunsigned_value [ptr v])]
|
||||
@function[(int Sinteger32_value [ptr v])]
|
||||
@function[(long Sunsigned32_value [ptr v])]
|
||||
@function[(long Sinteger64_value [ptr v])]
|
||||
@function[(unsigned-long Sunsigned64_value [ptr v])]
|
||||
)]{
|
||||
|
||||
Converts a Racket integer (possibly a bignum) to a C integer, assuming
|
||||
that the integer fits in the return type.}
|
||||
|
||||
@function[(ptr Sflonum [double f])]{
|
||||
|
||||
Returns a Racket flonum value.}
|
||||
|
||||
@function[(double Sflonum_value [ptr v])]{
|
||||
|
||||
Converts a Racket flonum value to a C floating-point number.}
|
||||
|
||||
|
||||
@function[(ptr Schar [int ch])]{
|
||||
|
||||
Returns a Racket character value. The @var{ch} value must be a legal
|
||||
Unicode code point (and not a surrogate, for example). All characters
|
||||
are represented by constant values.}
|
||||
|
||||
|
||||
@function[(ptr Schar_value [ptr ch])]{
|
||||
|
||||
Returns the Unicode code point for the Racket character @var{ch}.}
|
||||
|
||||
|
||||
@function[(ptr Sboolean [int bool])]{
|
||||
|
||||
Returns @cppi{Strue} or @cppi{Sfalse}.}
|
||||
|
||||
|
||||
@function[(ptr Scons [ptr car] [ptr cdr])]{
|
||||
|
||||
Makes a @racket[cons] pair.}
|
||||
|
||||
@together[(
|
||||
@function[(ptr Scar [ptr pr])]
|
||||
@function[(ptr Scdr [ptr pr])]
|
||||
)]{
|
||||
|
||||
Extracts the @racket[car] or @racket[cdr] of a pair.}
|
||||
|
||||
@function[(ptr Sstring_to_symbol [const-char* str])]{
|
||||
|
||||
Returns the interned symbol whose name matches @var{str}.}
|
||||
|
||||
@function[(ptr Ssymbol_to_string [ptr sym])]{
|
||||
|
||||
Returns the Racket immutable string value for the Racket symbol
|
||||
@var{sym}.}
|
||||
|
||||
@together[(
|
||||
@function[(ptr Smake_string [iptr len] [int ch])]
|
||||
@function[(ptr Smake_uninitialized_string [iptr len])]
|
||||
)]{
|
||||
|
||||
Allocates a fresh Racket mutable string with @var{len} characters. The
|
||||
content of the string is either all @var{ch}s when @var{ch} is
|
||||
provided or unspecified otherwise.}
|
||||
|
||||
@together[(
|
||||
@function[(ptr Sstring [const-char* str])]
|
||||
@function[(ptr Sstring_of_length [const-char* str] [iptr len])]
|
||||
@function[(ptr Sstring_utf8 [const-char* str] [iptr len])]
|
||||
)]{
|
||||
|
||||
Allocates a fresh Racket mutable string with the content of @var{str}.
|
||||
If @var{len} is not provided, @var{str} must be nul-terminated.
|
||||
In the case of @cppi{Sstring_utf8}, @var{str} is decoded as
|
||||
UTF-8, otherwise it is decided as Latin-1.}
|
||||
|
||||
|
||||
@function[(uptr string_length [ptr str])]{
|
||||
|
||||
Returns the length of the string @var{str}.}
|
||||
|
||||
@function[(ptr Sstring_ref [ptr str] [i uptr])]{
|
||||
|
||||
Returns the @var{i}th Racket character of the string @var{str}.}
|
||||
|
||||
@function[(int Sstring_set [ptr str] [i uptr] [ptr ch])]{
|
||||
|
||||
Installs @var{ch} as the @var{i}th Racket character of the string @var{str}.}
|
||||
|
||||
|
||||
|
||||
@function[(ptr Smake_vector [iptr len] [ptr v])]{
|
||||
|
||||
Allocates a fresh mutable @tech[#:doc reference-doc]{vector} of length
|
||||
@var{len} and with @var{v} initially in every slot.}
|
||||
|
||||
|
||||
@function[(uptr Svector_length [ptr vec])]{
|
||||
|
||||
Returns the length of the vector @var{vec}.}
|
||||
|
||||
|
||||
@function[(uptr Svector_ref [ptr vec] [i uptr])]{
|
||||
|
||||
Returns the @var{i}th element of the vector @var{vec}.}
|
||||
|
||||
|
||||
@function[(void Svector_set [ptr vec] [i uptr] [ptr v])]{
|
||||
|
||||
Installs @var{v} as the @var{i}th element of the vector @var{vec}.}
|
||||
|
||||
|
||||
@function[(ptr Smake_fxvector [iptr len] [ptr v])]{
|
||||
|
||||
Allocates a fresh mutable @tech[#:doc reference-doc]{fxvector} of
|
||||
length @var{len} and with @var{v} initially in every slot.}
|
||||
|
||||
|
||||
@function[(uptr Sfxvector_length [ptr vec])]{
|
||||
|
||||
Returns the length of the fxvector @var{vec}.}
|
||||
|
||||
|
||||
@function[(uptr Sfxvector_ref [ptr vec] [i uptr])]{
|
||||
|
||||
Returns the @var{i}th fixnum of the fxvector @var{vec}.}
|
||||
|
||||
|
||||
@function[(void Sfxvector_set [ptr vec] [i uptr] [ptr v])]{
|
||||
|
||||
Installs the fixnum @var{v} as the @var{i}th element of the fxvector
|
||||
@var{vec}.}
|
||||
|
||||
|
||||
|
||||
@function[(ptr Smake_bytevector [iptr len] [int byte])]{
|
||||
|
||||
Allocates a fresh mutable @tech[#:doc reference-doc]{byte string} of
|
||||
length @var{len} and with @var{byte} initially in every slot.}
|
||||
|
||||
@function[(uptr Sbytevector_length [ptr bstr])]{
|
||||
|
||||
Returns the length of the byte string @var{bstr}.}
|
||||
|
||||
@function[(int Sbytevector_u8_ref [ptr bstr] [i uptr])]{
|
||||
|
||||
Returns the @var{i}th byte of the byte string @var{bstr}.}
|
||||
|
||||
@function[(int Sbytevector_u8_set [ptr bstr] [i uptr] [int byte])]{
|
||||
|
||||
Installs @var{byte} as the @var{i}th byte of the byte string @var{bstr}.}
|
||||
|
||||
@function[(char* Sbytevector_data [ptr vec])]{
|
||||
|
||||
Returns a pointer to the start of the bytes for the byte string @var{bstr}.}
|
||||
|
||||
|
||||
@function[(ptr Sbox [ptr v])]{
|
||||
|
||||
Allocates a fresh mutable @tech[#:doc reference-doc]{box} containing
|
||||
@var{v}.}
|
||||
|
||||
@function[(ptr Sunbox [ptr bx])]{
|
||||
|
||||
Extract the content of the box @var{bx}.}
|
||||
|
||||
@function[(ptr Sset_box [ptr bx] [ptr v])]{
|
||||
|
||||
Installs @var{v} as the content of the box @var{bx}.}
|
16
pkgs/racket-doc/scribblings/inside/cs.scrbl
Normal file
16
pkgs/racket-doc/scribblings/inside/cs.scrbl
Normal file
|
@ -0,0 +1,16 @@
|
|||
#lang scribble/base
|
||||
|
||||
@title[#:style '(grouper toc) #:tag "cs"]{Inside Racket CS}
|
||||
|
||||
The Racket CS API is a small extension of the Chez Scheme C API as
|
||||
described in @italic{The Chez Scheme User's Guide}.
|
||||
|
||||
@local-table-of-contents[]
|
||||
|
||||
@include-section["cs-overview.scrbl"]
|
||||
@include-section["cs-embedding.scrbl"]
|
||||
@include-section["cs-values.scrbl"]
|
||||
@include-section["cs-procs.scrbl"]
|
||||
@include-section["cs-start.scrbl"]
|
||||
@include-section["cs-eval.scrbl"]
|
||||
@include-section["cs-thread.scrbl"]
|
|
@ -6,7 +6,7 @@
|
|||
|
||||
@title[#:tag "embedding"]{Embedding into a Program}
|
||||
|
||||
@section-index["embedding Racket"]
|
||||
@section-index["embedding Racket BC"]
|
||||
|
||||
The Racket run-time system can be embedded into a larger program. The
|
||||
embedding process for Racket CGC or Racket 3m (see @secref[cgc-v-3m])
|
||||
|
@ -66,7 +66,7 @@ To embed Racket CGC in a program, follow these steps:
|
|||
an executable-relative path using the Mach-O @tt["@executable_path"]
|
||||
prefix).}
|
||||
|
||||
@item{For each C/C++ file that uses Racket library functions,
|
||||
@item{For each C file that uses Racket library functions,
|
||||
@cpp{#include} the file @as-index{@filepath{scheme.h}}.
|
||||
|
||||
The C preprocessor symbol @cppi{SCHEME_DIRECT_EMBEDDED} is defined
|
||||
|
@ -122,7 +122,7 @@ To embed Racket CGC in a program, follow these steps:
|
|||
that contains modules in bytecode form as encapsulated in a static
|
||||
array. The generated C file defines a @cppi{declare_modules}
|
||||
function that takes a @cpp{Scheme_Env*}, installs the modules into
|
||||
the environment, and adjusts the module name resolver to access the
|
||||
the environment, and it adjusts the module name resolver to access the
|
||||
embedded declarations. If embedded modules refer to runtime files
|
||||
that need to be carried along, supply @DFlag{runtime} to
|
||||
@exec{raco ctool --c-mods} to collect the runtime files into a
|
||||
|
|
|
@ -11,6 +11,7 @@ and using the @seclink["top" #:doc '(lib
|
|||
usually a better option than writing an extension to Racket, but
|
||||
Racket also supports C-implemented extensions that plug more directly
|
||||
into the run-time system.
|
||||
(Racket CS does not have a similar extension interface.)
|
||||
|
||||
The process of creating an extension for Racket 3m or Racket CGC (see
|
||||
@secref["CGC versus 3m"]) is essentially the same, but the process for
|
||||
|
|
|
@ -6,13 +6,15 @@
|
|||
|
||||
@author["Matthew Flatt"]
|
||||
|
||||
This manual describes the C interface of Racket's runtime system for
|
||||
the 3m and CGC variants of Racket (but not the CS variant; see
|
||||
@secref[#:doc '(lib "scribblings/guide/guide.scrbl")
|
||||
"virtual-machines"]). The C
|
||||
interface is relevant primarily when interacting with foreign
|
||||
libraries as described in @other-manual['(lib
|
||||
"scribblings/foreign/foreign.scrbl")]; even though interactions with
|
||||
This manual describes the C interface of Racket's runtime system,
|
||||
which varies depending on the variant of Racket (see @secref[#:doc
|
||||
'(lib "scribblings/guide/guide.scrbl") "virtual-machines"]): the CS
|
||||
variant of Racket has one interface, while the BC (3m and CGC)
|
||||
variants of Racket have another.
|
||||
|
||||
The C interface is relevant to some degree when interacting with
|
||||
foreign libraries as described in @other-manual['(lib
|
||||
"scribblings/foreign/foreign.scrbl")]. Even though interactions with
|
||||
foreign code are constructed in pure Racket using the
|
||||
@racketmodname[ffi/unsafe] module, many details of representations,
|
||||
memory management, and concurrency are described here. This manual
|
||||
|
@ -23,26 +25,8 @@ and extending Racket directly with C-implemented libraries.
|
|||
|
||||
@; ------------------------------------------------------------------------
|
||||
|
||||
@include-section["overview.scrbl"]
|
||||
@include-section["embedding.scrbl"]
|
||||
@include-section["extensions.scrbl"]
|
||||
@include-section["values.scrbl"]
|
||||
@include-section["memory.scrbl"]
|
||||
@include-section["namespaces.scrbl"]
|
||||
@include-section["procedures.scrbl"]
|
||||
@include-section["eval.scrbl"]
|
||||
@include-section["exns.scrbl"]
|
||||
@include-section["threads.scrbl"]
|
||||
@include-section["params.scrbl"]
|
||||
@include-section["contmarks.scrbl"]
|
||||
@include-section["strings.scrbl"]
|
||||
@include-section["numbers.scrbl"]
|
||||
@include-section["ports.scrbl"]
|
||||
@include-section["structures.scrbl"]
|
||||
@include-section["security.scrbl"]
|
||||
@include-section["custodians.scrbl"]
|
||||
@include-section["subprocesses.scrbl"]
|
||||
@include-section["misc.scrbl"]
|
||||
@include-section["cs.scrbl"]
|
||||
@include-section["bc.scrbl"]
|
||||
|
||||
@; ------------------------------------------------------------------------
|
||||
|
||||
|
|
|
@ -20,7 +20,7 @@ all should be renamed to start @cpp{racket_}.
|
|||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section{Building Racket from Source}
|
||||
@section{Building Racket BC from Source}
|
||||
|
||||
The normal Racket distribution includes @filepath{.rkt} sources for
|
||||
collection-based libraries. After modifying library files, run
|
||||
|
@ -93,7 +93,7 @@ to call the library.
|
|||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section[#:tag "places"]{Racket and Places}
|
||||
@section[#:tag "places"]{Racket BC and Places}
|
||||
|
||||
Each Racket @|tech-place| corresponds to a separate OS-implemented
|
||||
thread. Each place has its own memory manager. Pointers to GC-managed
|
||||
|
@ -118,15 +118,13 @@ for the original place.
|
|||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section{Racket and Threads}
|
||||
@section{Racket BC and Threads}
|
||||
|
||||
Racket implements threads for Racket programs without aid from the
|
||||
operating system, so that Racket threads are cooperative from the
|
||||
perspective of C code. On Unix, stand-alone Racket uses a single
|
||||
OS-implemented thread. On Windows and Mac OS, stand-alone
|
||||
Racket uses a few private OS-implemented threads for background
|
||||
tasks, but these OS-implemented threads are never exposed by the
|
||||
Racket API.
|
||||
perspective of C code. Stand-alone Racket may uses a few private
|
||||
OS-implemented threads for background tasks, but these OS-implemented
|
||||
threads are never exposed by the Racket API.
|
||||
|
||||
Racket can co-exist with additional OS-implemented threads, but the
|
||||
additional OS threads must not call any @cpp{scheme_} function. Only
|
||||
|
@ -146,7 +144,7 @@ and embedding C code.
|
|||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section[#:tag "im:unicode"]{Racket, Unicode, Characters, and Strings}
|
||||
@section[#:tag "im:unicode"]{Racket BC, Unicode, Characters, and Strings}
|
||||
|
||||
A character in Racket is a Unicode code point. In C, a character
|
||||
value has type @cppi{mzchar}, which is an alias for @cpp{unsigned} ---
|
||||
|
@ -163,7 +161,7 @@ See also @secref["im:strings"] and @secref["im:encodings"].
|
|||
|
||||
@; ----------------------------------------------------------------------
|
||||
|
||||
@section[#:tag "im:intsize"]{Integers}
|
||||
@section[#:tag "im:intsize"]{Racket BC Integers}
|
||||
|
||||
Racket expects to be compiled in a mode where @cppi{short} is a
|
||||
16-bit integer, @cppi{int} is a 32-bit integer, and @cppi{intptr_t} has
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
|
||||
(provide Racket
|
||||
mzc cpp cppi cppdef (rename-out [*var var])
|
||||
function subfunction
|
||||
function subfunction together
|
||||
FormatD
|
||||
tech-place
|
||||
reference-doc raco-doc
|
||||
|
@ -121,6 +121,19 @@
|
|||
(loop (cdr types) (cdr args)))))))))
|
||||
(rest-thunk)))))
|
||||
|
||||
(define-syntax-rule (together (func ...) expl ...)
|
||||
(together*
|
||||
(list func ...)
|
||||
(lambda () (list expl ...))))
|
||||
|
||||
(define (together* funcs body-thunk)
|
||||
(make-splice
|
||||
(cons
|
||||
(make-table
|
||||
'boxed
|
||||
(map table-blockss (map car (map splice-run funcs))))
|
||||
(body-thunk))))
|
||||
|
||||
(define (boxed t)
|
||||
(make-table
|
||||
'boxed
|
||||
|
|
|
@ -10,15 +10,18 @@
|
|||
|
||||
The @DFlag{c-mods} mode for @exec{raco ctool} takes a set of Racket
|
||||
modules and generates a C source file that can be used as part of
|
||||
program that embeds the Racket run-time system. See @secref[#:doc
|
||||
program that embeds the Racket runtime system. See @secref[#:doc
|
||||
inside-doc "embedding"] in @other-manual[inside-doc] for an
|
||||
explanation of embedding programs.
|
||||
explanation of embedding programs. The @DFlag{mods} mode is similar, but
|
||||
it generates the raw bytes for the compiled module without encoding
|
||||
the bytes in C declarations.
|
||||
|
||||
The generated source file embeds the specified modules, and it defines
|
||||
a @tt{declare_modules} function that puts the module declarations into
|
||||
a namespace. Thus, using the output of @exec{raco ctool --c-mods}, a
|
||||
program can embed Racket with a set of modules so that it does not
|
||||
need a @filepath{collects} directory to load modules at run time.
|
||||
The generated source or compiled file embeds the specified modules.
|
||||
Generated C source defines a @tt{declare_modules} function that puts
|
||||
the module declarations into a namespace. Thus, using the output of
|
||||
@exec{raco ctool --c-mods}, a program can embed Racket with a set of
|
||||
modules so that it does not need a @filepath{collects} directory to
|
||||
load modules at run time.
|
||||
|
||||
If the embedded modules refer to runtime files, the files can be
|
||||
gathered by supplying the @DFlag{runtime} argument to @exec{raco ctool
|
||||
|
|
|
@ -57,7 +57,7 @@
|
|||
(let ([b (path-element->bytes
|
||||
(let-values ([(base name dir?) (split-path f)])
|
||||
name))])
|
||||
(or (regexp-match? #rx#"[.](?i:pdb|ilk|manifest)$" b)
|
||||
(or (regexp-match? #rx#"[.](?i:pdb|ilk|manifest|ipdb|iobj)$" b)
|
||||
(and (not keep-cgc?)
|
||||
(regexp-match? #rx#"(?i:CGC[.](?:dll|exe))$" b))
|
||||
(and (not keep-3m?)
|
||||
|
|
9
racket/src/ac/instlib.m4
Normal file
9
racket/src/ac/instlib.m4
Normal file
|
@ -0,0 +1,9 @@
|
|||
show_explicitly_enabled "${enable_libs}" "Installation of static libraries (if any)"
|
||||
show_explicitly_disabled "${enable_libs}" "Installation of static libraries (if any)"
|
||||
|
||||
INSTALL_LIBS_ENABLE=no-install
|
||||
|
||||
if test "${enable_libs}" != "no" ; then
|
||||
# Intended to be canceled for some platforms:
|
||||
INSTALL_LIBS_ENABLE=install
|
||||
fi
|
1
racket/src/ac/instlib_arg.m4
Normal file
1
racket/src/ac/instlib_arg.m4
Normal file
|
@ -0,0 +1 @@
|
|||
AC_ARG_ENABLE(libs, [ --enable-libs install static libraries (enabled by default for Unix)])
|
|
@ -2734,6 +2734,7 @@ if test "${enable_libs+set}" = set; then :
|
|||
fi
|
||||
|
||||
|
||||
|
||||
# Check whether --enable-libffi was given.
|
||||
if test "${enable_libffi+set}" = set; then :
|
||||
enableval=$enable_libffi;
|
||||
|
@ -3284,6 +3285,14 @@ show_explicitly_disabled "${enable_strip}" "Debug-symbol stripping"
|
|||
show_explicitly_enabled "${enable_libs}" "Installation of static libraries (if any)"
|
||||
show_explicitly_disabled "${enable_libs}" "Installation of static libraries (if any)"
|
||||
|
||||
INSTALL_LIBS_ENABLE=no-install
|
||||
|
||||
if test "${enable_libs}" != "no" ; then
|
||||
# Intended to be canceled for some platforms:
|
||||
INSTALL_LIBS_ENABLE=install
|
||||
fi
|
||||
|
||||
|
||||
show_explicitly_disabled "${enable_mac64}" "64-bit Mac OS"
|
||||
|
||||
show_explicitly_enabled "${enable_libfw}" "Frameworks-to-system"
|
||||
|
@ -3419,8 +3428,6 @@ MAIN_VARIANT=3m
|
|||
INSTALL_SETUP_FLAGS=
|
||||
INSTALL_SETUP_RACKET_FLAGS=
|
||||
|
||||
INSTALL_LIBS_ENABLE=no-install
|
||||
|
||||
use_flag_pthread=yes
|
||||
use_flag_posix_pthread=no
|
||||
mzrt_needs_pthread=yes
|
||||
|
@ -4804,11 +4811,6 @@ if test "${enable_jit}" = "yes" ; then
|
|||
check_for_mprotect=yes
|
||||
fi
|
||||
|
||||
if test "${enable_libs}" != "no" ; then
|
||||
# Canceled for some platforms below:
|
||||
INSTALL_LIBS_ENABLE=install
|
||||
fi
|
||||
|
||||
############## platform tests ################
|
||||
|
||||
# for flags we don't want to use in config tests:
|
||||
|
|
|
@ -22,7 +22,7 @@ CROSS_COMP =
|
|||
COMPILE_FILE = $(SCHEME) --script compile-file.ss $(UNSAFE_COMP) $(COMPRESS_COMP) $(DEBUG_COMP) $(CROSS_COMP) --dest "$(BUILDDIR)"
|
||||
COMPILE_FILE_DEPS = compile-file.ss include.ss place-register.ss
|
||||
|
||||
RACKET_SETUP_ARGS = ../../bin/racket ../../bin/racket ../collects ../etc 0 true false 0 ""
|
||||
RACKET_SETUP_ARGS = false ../../bin/racket ../../bin/racket ../collects ../etc 0 true false 0 ""
|
||||
|
||||
PRIMITIVES_TABLES = primitive/kernel.ss primitive/unsafe.ss primitive/flfxnum.ss \
|
||||
primitive/paramz.ss primitive/extfl.ss primitive/network.ss \
|
||||
|
|
|
@ -26,6 +26,9 @@ WINDRES = @WINDRES@
|
|||
STRIP_DEBUG = @STRIP_DEBUG@
|
||||
STRIP_LIB_DEBUG = @STRIP_LIB_DEBUG@
|
||||
|
||||
ICP=@ICP@
|
||||
ICP_LIB=@ICP_LIB@
|
||||
|
||||
DEFAULT_RACKET = ../../racket/racket3m
|
||||
RACKET = @RACKET@
|
||||
|
||||
|
@ -61,6 +64,7 @@ cs:
|
|||
$(MAKE) check-racketcs@CROSS_MODE@
|
||||
$(MAKE) gracketcs
|
||||
$(MAKE) starter
|
||||
$(MAKE) repack-@INSTALL_LIBS_ENABLE@-libs
|
||||
|
||||
SETUP_BOOT_MODE = @SETUP_BOOT_MODE@
|
||||
SETUP_COMMON_BOOT = -l- setup $(SETUP_BOOT_MODE) $(srcdir)/../../setup-go.rkt $(builddir)/compiled
|
||||
|
@ -344,6 +348,7 @@ install@MINGW@:
|
|||
|
||||
plain-install@MINGW@:
|
||||
$(MAKE) plain-install-upcased CS_INSTALLED=`echo $(CS_INSTALLED) | awk '{print toupper($0)}'`
|
||||
$(MAKE) unix-install-boot-files
|
||||
|
||||
plain-install-upcased:
|
||||
$(ICP) libracketcsxxxxxxx.dll $(libdir)/libracketcsxxxxxxx.dll
|
||||
|
@ -395,11 +400,25 @@ boot.o: $(srcdir)/boot.c $(srcdir)/../../rktio/rktio.inc $(srcdir)/boot.h
|
|||
starter@NOT_MINGW@: $(srcdir)/../../start/ustart.c
|
||||
$(CC) $(CFLAGS) -o starter $(srcdir)/../../start/ustart.c
|
||||
|
||||
|
||||
repack-install-libs:
|
||||
make libracketcs.a SCHEME_SRC="$(ABS_SCHEME_SRC)"
|
||||
|
||||
libracketcs.a: $(SCHEME_LIB_DEPS) rktio/librktio.a boot.o
|
||||
mkdir -p repack
|
||||
rm -f repack/*
|
||||
cd repack && @Z_LIB_UNPACK@
|
||||
cd repack && @LZ4_LIB_UNPACK@
|
||||
cd repack && $(AR) x ../rktio/librktio.a
|
||||
cd repack && $(AR) x $(SCHEME_TARGET_INC)/libkernel.a
|
||||
$(AR) $(ARFLAGS) libracketcs.a repack/*.o boot.o
|
||||
|
||||
repack-no-install-libs:
|
||||
$(NOOP)
|
||||
|
||||
# ----------------------------------------
|
||||
# Install
|
||||
|
||||
ICP=@ICP@
|
||||
|
||||
install@NOT_MINGW@:
|
||||
$(MAKE) plain-install
|
||||
$(MAKE) setup-install
|
||||
|
@ -438,16 +457,39 @@ common-install:
|
|||
$(ICP) $(srcdir)/../../start/starter-sh "$(DESTDIR)$(libpltdir)/starter-sh"
|
||||
$(RACKET) -cu "$(srcdir)/../../racket/collects-path.rkt" "$(DESTDIR)$(libpltdir)/starter" $(DESTDIR)@COLLECTS_PATH@ $(DESTDIR)@CONFIG_PATH@
|
||||
$(MAKE) system-install
|
||||
$(ICP) $(srcdir)/api.h $(includepltdir)/racketcs.h
|
||||
$(ICP) $(srcdir)/boot.h $(includepltdir)/racketcsboot.h
|
||||
$(ICP) $(SCHEME_INC)/scheme.h $(includepltdir)/chezscheme.h
|
||||
$(MAKE) common-@INSTALL_LIBS_ENABLE@-libs
|
||||
|
||||
system-install:
|
||||
$(RACKET) -cu "$(srcdir)/gen-system.rkt" $(DESTDIR)$(libpltdir)/system$(CS_INSTALLED).rktd $(TARGET_MACH) @CROSS_COMPILE_TARGET_KIND@
|
||||
|
||||
common-install-libs:
|
||||
$(ICP_LIB) libracketcs.a "$(DESTDIR)$(libdir)/libracketcs.a"
|
||||
$(STRIP_LIB_DEBUG) "$(DESTDIR)$(libdir)/libracketcs.a"
|
||||
|
||||
common-no-install-libs:
|
||||
$(NOOP)
|
||||
|
||||
unix-install:
|
||||
$(MAKE) common-install
|
||||
rm -f "$(DESTDIR)$(libpltdir)/gracket$(CS_INSTALLED)"
|
||||
$(ICP) gracketcs "$(DESTDIR)$(libpltdir)/gracket$(CS_INSTALLED)"
|
||||
$(RACKET) -cu "$(srcdir)/../../racket/collects-path.rkt" "$(DESTDIR)$(bindir)/racket$(CS_INSTALLED)" $(DESTDIR)@COLLECTS_PATH@ $(DESTDIR)@CONFIG_PATH@
|
||||
$(RACKET) -cu "$(srcdir)/../../racket/collects-path.rkt" "$(DESTDIR)$(libpltdir)/gracket$(CS_INSTALLED)" $(DESTDIR)@COLLECTS_PATH@ $(DESTDIR)@CONFIG_PATH@
|
||||
$(MAKE) unix-@INSTALL_LIBS_ENABLE@-libs
|
||||
|
||||
unix-install-libs:
|
||||
$(MAKE) unix-install-boot-files
|
||||
|
||||
unix-install-boot-files:
|
||||
$(BOOTSTRAP_RACKET) $(srcdir)/add-terminator.rkt petite-v.boot "$(DESTDIR)$(libpltdir)/petite.boot"
|
||||
$(BOOTSTRAP_RACKET) $(srcdir)/add-terminator.rkt scheme-v.boot "$(DESTDIR)$(libpltdir)/scheme.boot"
|
||||
$(BOOTSTRAP_RACKET) $(srcdir)/add-terminator.rkt racket-v.boot "$(DESTDIR)$(libpltdir)/racket.boot"
|
||||
|
||||
unix-no-install-libs:
|
||||
$(NOOP)
|
||||
|
||||
RKTFWDEST = @FRAMEWORK_INSTALL_DIR@/Racket.framework
|
||||
FRAMEWORK_REL_PREFIX = "@executable_path/../$(libpltdir_rel)/"
|
||||
|
@ -469,6 +511,7 @@ macos-install:
|
|||
cp $(RKTFWDIR)/boot/racket.boot $(DESTDIR)$(RKTFWDEST)/Versions/$(FWVERSION)_CS/boot/
|
||||
$(RACKET) -cu "$(srcdir)/../../racket/collects-path.rkt" "$(DESTDIR)$(bindir)/racket$(CS_INSTALLED)" $(DESTDIR)@COLLECTS_PATH@ $(DESTDIR)@CONFIG_PATH@
|
||||
$(MAKE) macos-install-gracket CS_GR_INSTALLED="`echo $(CS_INSTALLED) | tr a-z A-Z`"
|
||||
$(MAKE) macos-@INSTALL_LIBS_ENABLE@-libs
|
||||
|
||||
macos-install-gracket:
|
||||
/usr/bin/install_name_tool -change "@executable_path/Racket.framework/Versions/$(FWVERSION)_CS/Racket" "@FRAMEWORK_PREFIX@Racket.framework/Versions/$(FWVERSION)_CS/Racket" $(DESTDIR)"$(bindir)/racket$(CS_INSTALLED)"
|
||||
|
@ -481,6 +524,14 @@ macos-install-gracket:
|
|||
rm -rf $(DESTDIR)"$(libpltdir)/Starter.app"
|
||||
$(ICP) -r Starter.app $(DESTDIR)"$(libpltdir)/."
|
||||
|
||||
macos-install-libs:
|
||||
$(BOOTSTRAP_RACKET) $(srcdir)/add-terminator.rkt $(RKTFWDIR)/boot/petite.boot "$(DESTDIR)$(libpltdir)/petite.boot"
|
||||
$(BOOTSTRAP_RACKET) $(srcdir)/add-terminator.rkt $(RKTFWDIR)/boot/scheme.boot "$(DESTDIR)$(libpltdir)/scheme.boot"
|
||||
$(BOOTSTRAP_RACKET) $(srcdir)/add-terminator.rkt $(RKTFWDIR)/boot/racket.boot "$(DESTDIR)$(libpltdir)/racket.boot"
|
||||
|
||||
macos-no-install-libs:
|
||||
$(NOOP)
|
||||
|
||||
# ----------------------------------------
|
||||
# Check
|
||||
|
||||
|
|
28
racket/src/cs/c/add-terminator.rkt
Normal file
28
racket/src/cs/c/add-terminator.rkt
Normal file
|
@ -0,0 +1,28 @@
|
|||
#lang racket/base
|
||||
(require racket/cmdline)
|
||||
|
||||
(command-line
|
||||
#:args
|
||||
(src dest)
|
||||
|
||||
(copy-file src dest #t)
|
||||
|
||||
(define terminator
|
||||
(cond
|
||||
[(equal? #"\0\0\0\0chez" (call-with-input-file*
|
||||
dest
|
||||
(lambda (i) (read-bytes 8 i))))
|
||||
;; Not compressed
|
||||
#"\177"]
|
||||
[else
|
||||
;; Compressed
|
||||
#"\0"]))
|
||||
|
||||
(call-with-output-file*
|
||||
dest
|
||||
#:exists 'update
|
||||
(lambda (o)
|
||||
(file-position o (file-size dest))
|
||||
(write-bytes terminator o)))
|
||||
|
||||
(void))
|
27
racket/src/cs/c/api.h
Normal file
27
racket/src/cs/c/api.h
Normal file
|
@ -0,0 +1,27 @@
|
|||
/* include "chezscheme.h" before this file */
|
||||
|
||||
#ifndef RACKETCS_H
|
||||
#define RACKETCS_H
|
||||
|
||||
#ifndef RACKET_API_EXTERN
|
||||
# define RACKET_API_EXTERN EXPORT
|
||||
#endif
|
||||
|
||||
#ifndef RACKETCS_BOOT_H
|
||||
# define BOOT_EXTERN EXPORT
|
||||
# include "racketcsboot.h"
|
||||
#endif
|
||||
|
||||
RACKET_API_EXTERN ptr racket_apply(ptr proc, ptr arg_list);
|
||||
|
||||
RACKET_API_EXTERN ptr racket_primitive(const char *name);
|
||||
|
||||
RACKET_API_EXTERN ptr racket_eval(ptr s_expr);
|
||||
RACKET_API_EXTERN ptr racket_dynamic_require(ptr module_path, ptr sym_or_false);
|
||||
RACKET_API_EXTERN void racket_namespace_require(ptr module_path);
|
||||
|
||||
RACKET_API_EXTERN void racket_embedded_load_bytes(const char *code, uptr len, int as_predefined);
|
||||
RACKET_API_EXTERN void racket_embedded_load_file(const char *path, int as_predefined);
|
||||
RACKET_API_EXTERN void racket_embedded_load_file_region(const char *path, uptr start, uptr end, int as_predefined);
|
||||
|
||||
#endif
|
|
@ -10,11 +10,13 @@
|
|||
#include "rktio.h"
|
||||
|
||||
#ifdef WIN32
|
||||
# define BOOT_EXTERN __declspec(dllexport)
|
||||
# define RACKET_API_EXTERN __declspec(dllexport)
|
||||
#else
|
||||
# define BOOT_EXTERN extern
|
||||
# define RACKET_API_EXTERN extern
|
||||
#endif
|
||||
#define BOOT_EXTERN RACKET_API_EXTERN
|
||||
#include "boot.h"
|
||||
#include "api.h"
|
||||
|
||||
#define RACKET_AS_BOOT
|
||||
|
||||
|
@ -26,45 +28,6 @@
|
|||
# define BOOT_O_BINARY 0
|
||||
#endif
|
||||
|
||||
#if defined(OS_X) && !defined(RACKET_XONX)
|
||||
|
||||
# include <mach-o/dyld.h>
|
||||
# define RACKET_USE_FRAMEWORK
|
||||
|
||||
const char *get_framework_path() {
|
||||
int i, c, len;
|
||||
const char *s;
|
||||
|
||||
c = _dyld_image_count();
|
||||
for (i = 0; i < c; i++) {
|
||||
s = _dyld_get_image_name(i);
|
||||
len = strlen(s);
|
||||
if ((len > 7) && !strcmp("/Racket", s + len - 7)) {
|
||||
char *s2;
|
||||
s2 = strdup(s);
|
||||
strcpy(s2 + len - 6, "boot");
|
||||
return s2;
|
||||
}
|
||||
}
|
||||
|
||||
return "???";
|
||||
}
|
||||
|
||||
char *path_append(const char *p1, char *p2) {
|
||||
int l1, l2;
|
||||
char *s;
|
||||
l1 = strlen(p1);
|
||||
l2 = strlen(p2);
|
||||
s = malloc(l1 + l2 + 2);
|
||||
memcpy(s, p1, l1);
|
||||
s[l1] = '/';
|
||||
memcpy(s + l1 + 1, p2, l2);
|
||||
s[l1+l2+1] = 0;
|
||||
return s;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
static ptr Sbytevector(char *s)
|
||||
{
|
||||
iptr len = strlen(s);
|
||||
|
@ -135,75 +98,42 @@ static void init_foreign()
|
|||
Sforeign_symbol("racket_errno", (void *)racket_errno);
|
||||
}
|
||||
|
||||
void racket_boot(int argc, char **argv, char *exec_file, char *run_file,
|
||||
char *boot_exe, long segment_offset,
|
||||
char *coldir, char *configdir, /* wchar_t * */void *dlldir,
|
||||
int is_embedded, int pos1, int pos2, int pos3,
|
||||
int cs_compiled_subdir, int is_gui,
|
||||
int wm_is_gracket_or_x11_arg_count,
|
||||
char *gracket_guid_or_x11_args,
|
||||
void *dll_open, void *dll_find_object, void *dll_close)
|
||||
/* exe argument already stripped from argv */
|
||||
void racket_boot(racket_boot_arguments_t *ba)
|
||||
{
|
||||
int fd;
|
||||
#ifdef RACKET_AS_BOOT
|
||||
int skip_racket_boot = 0;
|
||||
#endif
|
||||
#ifdef RACKET_USE_FRAMEWORK
|
||||
const char *fw_path;
|
||||
#endif
|
||||
int cross_server = 0;
|
||||
|
||||
#ifdef WIN32
|
||||
if (dlldir)
|
||||
rktio_set_dll_path((wchar_t *)dlldir);
|
||||
if (dll_open)
|
||||
rktio_set_dll_procs(dll_open, dll_find_object, dll_close);
|
||||
if (ba->dll_dir)
|
||||
rktio_set_dll_path((wchar_t *)ba->dll_dir);
|
||||
if (ba->dll_open)
|
||||
rktio_set_dll_procs(ba->dll_open, ba->dll_find_object, ba->dll_close);
|
||||
#endif
|
||||
|
||||
Sscheme_init(NULL);
|
||||
|
||||
if ((argc == 4) && !strcmp(argv[0], "--cross-server")) {
|
||||
if ((ba->argc == 4) && !strcmp(ba->argv[0], "--cross-server"))
|
||||
cross_server = 1;
|
||||
#ifdef RACKET_AS_BOOT
|
||||
skip_racket_boot = 1;
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifdef RACKET_USE_FRAMEWORK
|
||||
if (!is_embedded) {
|
||||
fw_path = get_framework_path();
|
||||
Sregister_boot_file(path_append(fw_path, "petite.boot"));
|
||||
Sregister_boot_file(path_append(fw_path, "scheme.boot"));
|
||||
# ifdef RACKET_AS_BOOT
|
||||
if (!skip_racket_boot)
|
||||
Sregister_boot_file(path_append(fw_path, "racket.boot"));
|
||||
# endif
|
||||
}
|
||||
#endif
|
||||
{
|
||||
int fd1, fd2;
|
||||
|
||||
if (is_embedded) {
|
||||
fd = open(boot_exe, O_RDONLY | BOOT_O_BINARY);
|
||||
|
||||
{
|
||||
int fd1, fd2;
|
||||
|
||||
fd1 = dup(fd);
|
||||
lseek(fd1, pos1, SEEK_SET);
|
||||
Sregister_boot_file_fd("petite", fd1);
|
||||
fd1 = open(ba->boot1_path, O_RDONLY | BOOT_O_BINARY);
|
||||
lseek(fd1, ba->boot1_offset, SEEK_SET);
|
||||
Sregister_boot_file_fd("petite", fd1);
|
||||
|
||||
fd2 = open(boot_exe, O_RDONLY | BOOT_O_BINARY);
|
||||
lseek(fd2, pos2, SEEK_SET);
|
||||
Sregister_boot_file_fd("scheme", fd2);
|
||||
fd2 = open(ba->boot2_path, O_RDONLY | BOOT_O_BINARY);
|
||||
lseek(fd2, ba->boot2_offset, SEEK_SET);
|
||||
Sregister_boot_file_fd("scheme", fd2);
|
||||
|
||||
# ifdef RACKET_AS_BOOT
|
||||
if (!skip_racket_boot) {
|
||||
fd = open(boot_exe, O_RDONLY | BOOT_O_BINARY);
|
||||
lseek(fd, pos3, SEEK_SET);
|
||||
Sregister_boot_file_fd("racket", fd);
|
||||
}
|
||||
# endif
|
||||
if (!cross_server) {
|
||||
int fd3;
|
||||
|
||||
fd3 = open(ba->boot3_path, O_RDONLY | BOOT_O_BINARY);
|
||||
lseek(fd3, ba->boot3_offset, SEEK_SET);
|
||||
Sregister_boot_file_fd("racket", fd3);
|
||||
}
|
||||
# endif
|
||||
}
|
||||
|
||||
Sbuild_heap(NULL, init_foreign);
|
||||
|
@ -211,7 +141,7 @@ void racket_boot(int argc, char **argv, char *exec_file, char *run_file,
|
|||
if (cross_server) {
|
||||
/* Don't run Racket as usual. Instead, load the patch
|
||||
file and run `serve-cross-compile` */
|
||||
run_cross_server(argv);
|
||||
run_cross_server(ba->argv);
|
||||
racket_exit(0);
|
||||
}
|
||||
|
||||
|
@ -220,20 +150,25 @@ void racket_boot(int argc, char **argv, char *exec_file, char *run_file,
|
|||
int i;
|
||||
char segment_offset_s[32], wm_is_gracket_s[32];
|
||||
|
||||
for (i = argc; i--; ) {
|
||||
l = Scons(Sbytevector(argv[i]), l);
|
||||
if (ba->argv) {
|
||||
for (i = ba->argc; i--; ) {
|
||||
l = Scons(Sbytevector(ba->argv[i]), l);
|
||||
}
|
||||
} else {
|
||||
l = Scons(Sbytevector("-n"), l);
|
||||
}
|
||||
l = Scons(Sbytevector(gracket_guid_or_x11_args), l);
|
||||
sprintf(wm_is_gracket_s, "%d", wm_is_gracket_or_x11_arg_count);
|
||||
l = Scons(Sbytevector(ba->gracket_guid_or_x11_args ? ba->gracket_guid_or_x11_args : ""), l);
|
||||
sprintf(wm_is_gracket_s, "%d", ba->wm_is_gracket_or_x11_arg_count);
|
||||
l = Scons(Sbytevector(wm_is_gracket_s), l);
|
||||
l = Scons(Sbytevector(is_gui ? "true" : "false"), l);
|
||||
l = Scons(Sbytevector(cs_compiled_subdir ? "true" : "false"), l);
|
||||
sprintf(segment_offset_s, "%ld", segment_offset);
|
||||
l = Scons(Sbytevector(ba->is_gui ? "true" : "false"), l);
|
||||
l = Scons(Sbytevector(ba->cs_compiled_subdir ? "true" : "false"), l);
|
||||
sprintf(segment_offset_s, "%ld", ba->segment_offset);
|
||||
l = Scons(Sbytevector(segment_offset_s), l);
|
||||
l = Scons(Sbytevector(configdir), l);
|
||||
l = Scons(parse_coldirs(coldir), l);
|
||||
l = Scons(Sbytevector(run_file), l);
|
||||
l = Scons(Sbytevector(exec_file), l);
|
||||
l = Scons(Sbytevector(ba->config_dir ? ba->config_dir : "etc"), l);
|
||||
l = Scons(parse_coldirs(ba->collects_dir ? ba->collects_dir : ""), l);
|
||||
l = Scons(Sbytevector(ba->run_file ? ba->run_file : ba->exec_file ), l);
|
||||
l = Scons(Sbytevector(ba->exec_file), l);
|
||||
l = Scons(Sbytevector(ba->exit_after ? "false" : "true"), l);
|
||||
|
||||
#ifdef RACKET_AS_BOOT
|
||||
{
|
||||
|
@ -249,19 +184,14 @@ void racket_boot(int argc, char **argv, char *exec_file, char *run_file,
|
|||
}
|
||||
|
||||
#ifndef RACKET_AS_BOOT
|
||||
# ifdef RACKET_USE_FRAMEWORK
|
||||
if (!is_embedded) {
|
||||
fd = open(path_append(fw_path, "racket.so"), O_RDONLY);
|
||||
pos3 = 0;
|
||||
}
|
||||
# endif
|
||||
|
||||
{
|
||||
ptr c, p;
|
||||
int f3;
|
||||
|
||||
if (pos3) lseek(fd, pos3, SEEK_SET);
|
||||
fd3 = open(ba->boot3_path, O_RDONLY | BOOT_O_BINARY);
|
||||
if (boot3_offset) lseek(fd3, ba->boot3_offset, SEEK_SET);
|
||||
c = Stop_level_value(Sstring_to_symbol("open-fd-input-port"));
|
||||
p = Scall1(c, Sfixnum(fd));
|
||||
p = Scall1(c, Sfixnum(fd3));
|
||||
Slock_object(p);
|
||||
c = Stop_level_value(Sstring_to_symbol("port-file-compressed!"));
|
||||
Scall1(c, p);
|
||||
|
@ -271,3 +201,83 @@ void racket_boot(int argc, char **argv, char *exec_file, char *run_file,
|
|||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
/* **************************************** */
|
||||
|
||||
enum {
|
||||
EMBEDDED_ENTRY_APPLY,
|
||||
EMBEDDED_ENTRY_PRIMITIVE_LOOKUP,
|
||||
EMBEDDED_ENTRY_EVAL,
|
||||
EMBEDDED_ENTRY_DYNAMIC_REQUIRE,
|
||||
EMBEDDED_ENTRY_NAMESPACE_REQUIRE,
|
||||
EMBEDDED_ENTRY_EMBEDDED_LOAD
|
||||
};
|
||||
|
||||
static ptr get_embedded_entry(int index)
|
||||
{
|
||||
ptr vec;
|
||||
|
||||
vec = Stop_level_value(Sstring_to_symbol("embedded-racket-entry-info"));
|
||||
return Svector_ref(vec, index);
|
||||
}
|
||||
|
||||
ptr racket_apply(ptr proc, ptr arg_list)
|
||||
{
|
||||
ptr app = get_embedded_entry(EMBEDDED_ENTRY_APPLY);
|
||||
|
||||
return Scall2(app, proc, arg_list);
|
||||
}
|
||||
|
||||
ptr racket_primitive(const char *name)
|
||||
{
|
||||
ptr prim_lookup = get_embedded_entry(EMBEDDED_ENTRY_PRIMITIVE_LOOKUP);
|
||||
|
||||
return Scall1(prim_lookup, Sstring_to_symbol(name));
|
||||
}
|
||||
|
||||
ptr racket_eval(ptr s_expr)
|
||||
{
|
||||
ptr eval = get_embedded_entry(EMBEDDED_ENTRY_EVAL);
|
||||
|
||||
return racket_apply(eval, Scons(s_expr, Snil));
|
||||
}
|
||||
|
||||
ptr racket_dynamic_require(ptr module_path, ptr sym_or_false)
|
||||
{
|
||||
ptr dy_req = get_embedded_entry(EMBEDDED_ENTRY_DYNAMIC_REQUIRE);
|
||||
|
||||
return racket_apply(dy_req, Scons(module_path, Scons(sym_or_false, Snil)));
|
||||
}
|
||||
|
||||
void racket_namespace_require(ptr module_path)
|
||||
{
|
||||
ptr ns_req = get_embedded_entry(EMBEDDED_ENTRY_NAMESPACE_REQUIRE);
|
||||
|
||||
(void)racket_apply(ns_req, Scons(module_path, Snil));
|
||||
}
|
||||
|
||||
static void embedded_load(ptr path, ptr start, ptr end, ptr bstr, int as_predefined)
|
||||
{
|
||||
ptr load = get_embedded_entry(EMBEDDED_ENTRY_EMBEDDED_LOAD);
|
||||
ptr pre = (as_predefined ? Strue : Sfalse);
|
||||
|
||||
(void)racket_apply(load, Scons(path, Scons(start, Scons(end, Scons(bstr, Scons(pre, Snil))))));
|
||||
}
|
||||
|
||||
void racket_embedded_load_bytes(const char *code, uptr len, int as_predefined)
|
||||
{
|
||||
ptr bstr = Smake_bytevector(len, 0);
|
||||
memcpy(Sbytevector_data(bstr), code, len);
|
||||
|
||||
embedded_load(Sfalse, Sfalse, Sfalse, bstr, as_predefined);
|
||||
}
|
||||
|
||||
void racket_embedded_load_file(const char *path, int as_predefined)
|
||||
{
|
||||
embedded_load(Sbytevector((char *)path), Sfixnum(0), Sfalse, Sfalse, as_predefined);
|
||||
}
|
||||
|
||||
void racket_embedded_load_file_region(const char *path, uptr start, uptr end, int as_predefined)
|
||||
{
|
||||
embedded_load(Sbytevector((char *)path), Sfixnum(start), Sfixnum(end), Sfalse, as_predefined);
|
||||
}
|
||||
|
|
|
@ -1,15 +1,57 @@
|
|||
BOOT_EXTERN void racket_boot(int argc, char **argv, char *exec_file, char *run_file,
|
||||
char *boot_exe, long segment_offset,
|
||||
char *coldir, char *configdir, /* wchar_t * */void *dlldir,
|
||||
int is_embedded, int pos1, int pos2, int pos3,
|
||||
int cs_compiled_subdir, int is_gui,
|
||||
int wm_is_gracket_or_x11_arg_count, char *gracket_guid_or_x11_args,
|
||||
void *ddll_open, void *dll_find_object, void *dll_close);
|
||||
#ifndef RACKETCS_BOOT_H
|
||||
#define RACKETCS_BOOT_H
|
||||
|
||||
typedef void (*racket_boot_t)(int argc, char **argv, char *exec_file, char *run_file,
|
||||
char* boot_exe, long segment_offset,
|
||||
char *coldir, char *configdir, /* wchar_t * */void *dlldir,
|
||||
int is_embedded, int pos1, int pos2, int pos3,
|
||||
int cs_compiled_subdir, int is_gui,
|
||||
int wm_is_gracket_or_x11_arg_count, char *gracket_guid_or_x11_args,
|
||||
void *ddll_open, void *dll_find_object, void *dll_close);
|
||||
/* This structure type can change, but NULL/0 will be supported as a
|
||||
default for any new field that is added. */
|
||||
typedef struct racket_boot_arguments_t {
|
||||
/* Boot files --- potentially the same path with different offsets.
|
||||
If a boot image is embedded in a larger file, it must be
|
||||
terminated with "\0 if the boot image is compressed or "\177" if
|
||||
the boot image is uncompressed. */
|
||||
const char *boot1_path; /* REQUIRED; path to "petite.boot" */
|
||||
long boot1_offset;
|
||||
const char *boot2_path; /* REQUIRED; path to "scheme.boot" */
|
||||
long boot2_offset;
|
||||
const char *boot3_path; /* REQUIRED; path to "racket.boot" */
|
||||
long boot3_offset;
|
||||
|
||||
/* Command-line arguments are handled in the same way as the
|
||||
`racket` exectuable. The `argv` array should *not* include the
|
||||
executable name like `argv` passed to `main`. */
|
||||
int argc;
|
||||
char **argv; /* NULL => "-n", which does nothing after booting */
|
||||
|
||||
/* Racket path configuration, mostly setting the results of
|
||||
`(find-system-path ...)`: */
|
||||
const char *exec_file; /* REQUIRED; usually the original argv[0] */
|
||||
const char *run_file; /* can be NULL to mean the same as `exec_file` */
|
||||
const char *collects_dir; /* can be NULL or "" to disable collection path */
|
||||
const char *config_dir; /* use NULL or "etc" if you don't care */
|
||||
/* wchar_t * */void *dll_dir; /* can be NULL for default */
|
||||
|
||||
/* How to initialize `use-compiled-file-paths`: */
|
||||
int cs_compiled_subdir; /* true => subdirectory of "compiled" */
|
||||
|
||||
/* Embedded-code offset, which is added to any `-k` argument. */
|
||||
long segment_offset; /* use 0 if no `-k` embedding */
|
||||
|
||||
/* For embedded DLLs on Windows, if non-NULL: */
|
||||
void *dll_open;
|
||||
void *dll_find_object;
|
||||
void *dll_close;
|
||||
|
||||
/* Whether to run as command-line Racket or in embedded mode: */
|
||||
int exit_after; /* 1 => exit after handling the command-line */
|
||||
|
||||
/* For GUI applications; use 0 and "" as defaults: */
|
||||
int is_gui;
|
||||
int wm_is_gracket_or_x11_arg_count;
|
||||
char *gracket_guid_or_x11_args;
|
||||
} racket_boot_arguments_t;
|
||||
|
||||
BOOT_EXTERN void racket_boot(racket_boot_arguments_t *boot_args);
|
||||
|
||||
/* Same as `racket_boot` prototype; but in type form: */
|
||||
typedef void (*racket_boot_t)(racket_boot_arguments_t *boot_args);
|
||||
|
||||
#endif
|
||||
|
|
34
racket/src/cs/c/configure
vendored
34
racket/src/cs/c/configure
vendored
|
@ -622,6 +622,7 @@ ac_includes_default="\
|
|||
|
||||
ac_subst_vars='LTLIBOBJS
|
||||
LIBOBJS
|
||||
INSTALL_LIBS_ENABLE
|
||||
INSTALL_SETUP_RACKET_FLAGS
|
||||
INSTALL_SETUP_FLAGS
|
||||
RUN_RACKET
|
||||
|
@ -640,8 +641,10 @@ ELF_COMP
|
|||
BOOT_COMPRESS_COMP
|
||||
COMPRESS_COMP
|
||||
CONFIGURE_RACKET_SO_COMPILE
|
||||
LZ4_LIB_UNPACK
|
||||
LZ4_LIB
|
||||
LZ4_LIB_DEP
|
||||
Z_LIB_UNPACK
|
||||
Z_LIB
|
||||
Z_LIB_DEP
|
||||
NOT_MINGW
|
||||
|
@ -664,6 +667,7 @@ POST_LINKER
|
|||
RKTLINKER
|
||||
STRIP_LIB_DEBUG
|
||||
STRIP_DEBUG
|
||||
ICP_LIB
|
||||
ICP
|
||||
WINDRES
|
||||
STATIC_AR
|
||||
|
@ -789,6 +793,7 @@ enable_libfw
|
|||
enable_userfw
|
||||
enable_embedfw
|
||||
enable_mac64
|
||||
enable_libs
|
||||
enable_noopt
|
||||
enable_ubsan
|
||||
enable_csdefault
|
||||
|
@ -1438,6 +1443,7 @@ Optional Features:
|
|||
--enable-userfw install Mac OS frameworks to ~/Library/Frameworks
|
||||
--enable-embedfw embed Mac OS framework content in executables
|
||||
--enable-mac64 allow 64-bit Mac OS build (enabled by default)
|
||||
--enable-libs install static libraries (enabled by default for Unix)
|
||||
--enable-strip strip debug on install (usually enabled by default)
|
||||
--enable-ubsan compile with -fsanitize=undefined
|
||||
--enable-csdefault use CS as default build
|
||||
|
@ -2648,6 +2654,12 @@ else
|
|||
fi
|
||||
|
||||
|
||||
# Check whether --enable-libs was given.
|
||||
if test "${enable_libs+set}" = set; then :
|
||||
enableval=$enable_libs;
|
||||
fi
|
||||
|
||||
|
||||
# Check whether --enable-noopt was given.
|
||||
if test "${enable_noopt+set}" = set; then :
|
||||
enableval=$enable_noopt;
|
||||
|
@ -2785,6 +2797,16 @@ if test "${enable_csonly}" = "yes" ; then
|
|||
fi
|
||||
show_explicitly_enabled "${enable_csdefault}" "executables without suffix"
|
||||
|
||||
show_explicitly_enabled "${enable_libs}" "Installation of static libraries (if any)"
|
||||
show_explicitly_disabled "${enable_libs}" "Installation of static libraries (if any)"
|
||||
|
||||
INSTALL_LIBS_ENABLE=no-install
|
||||
|
||||
if test "${enable_libs}" != "no" ; then
|
||||
# Intended to be canceled for some platforms:
|
||||
INSTALL_LIBS_ENABLE=install
|
||||
fi
|
||||
|
||||
show_explicitly_disabled "${enable_mac64}" "64-bit Mac OS"
|
||||
|
||||
show_explicitly_enabled "${enable_libfw}" "Frameworks-to-system"
|
||||
|
@ -3096,8 +3118,10 @@ INSTALL_SETUP_RACKET_FLAGS=
|
|||
|
||||
Z_LIB_DEP='$(OWN_Z_LIB)'
|
||||
Z_LIB='$(OWN_Z_LIB)'
|
||||
Z_LIB_UNPACK='$(AR) x $(OWN_Z_LIB)'
|
||||
LZ4_LIB_DEP='$(OWN_LZ4_LIB)'
|
||||
LZ4_LIB='$(OWN_LZ4_LIB)'
|
||||
LZ4_LIB_UNPACK='$(AR) x $(OWN_LZ4_LIB)'
|
||||
|
||||
enable_pthread_by_default=yes
|
||||
|
||||
|
@ -4603,6 +4627,10 @@ fi
|
|||
if `which ${host}-windres > /dev/null` ; then
|
||||
WINDRES="${host}-windres"
|
||||
fi
|
||||
# ".a" is typically not useful, since we always build a DLL:
|
||||
if test "${enable_libs}" = "" ; then
|
||||
INSTALL_LIBS_ENABLE=no-install
|
||||
fi
|
||||
;;
|
||||
cygwin*)
|
||||
;;
|
||||
|
@ -5239,6 +5267,7 @@ $as_echo "$have_zlib" >&6; }
|
|||
else
|
||||
Z_LIB_DEP=""
|
||||
Z_LIB="-lz"
|
||||
Z_LIB_UNPACK="$(NOOP)"
|
||||
extra_scheme_config_args="${extra_scheme_config_args} ZLIB=-lz"
|
||||
fi
|
||||
fi
|
||||
|
@ -5276,6 +5305,7 @@ $as_echo "$have_lz4" >&6; }
|
|||
else
|
||||
LZ4_LIB_DEP=""
|
||||
LZ4_LIB="-llz4"
|
||||
LZ4_LIB_UNPACK="$(NOOP)"
|
||||
extra_scheme_config_args="${extra_scheme_config_args} LZ4=-llz4"
|
||||
fi
|
||||
fi
|
||||
|
@ -5474,6 +5504,10 @@ SCHEME_CROSS_CONFIG_ARGS="--machine=${TARGET_MACH} --disable-x11 ${disable_curse
|
|||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
|
|
@ -25,6 +25,7 @@ AC_ARG_ENABLE(mach, [ --enable-mach=<mach> Use Chez Scheme machine typ
|
|||
AC_ARG_ENABLE(target, [ --enable-target=<mach> Cross-build for Chez Scheme machine type <mach>])
|
||||
m4_include(../ac/natipkg_arg.m4)
|
||||
m4_include(../ac/sdk_arg.m4)
|
||||
m4_include(../ac/instlib_arg.m4)
|
||||
m4_include(../ac/strip_arg.m4)
|
||||
m4_include(../ac/ubsan_arg.m4)
|
||||
AC_ARG_ENABLE(csdefault, [ --enable-csdefault use CS as default build])
|
||||
|
@ -86,6 +87,7 @@ if test "${enable_csonly}" = "yes" ; then
|
|||
fi
|
||||
show_explicitly_enabled "${enable_csdefault}" "executables without suffix"
|
||||
|
||||
m4_include(../ac/instlib.m4)
|
||||
m4_include(../ac/sdk_show.m4)
|
||||
m4_include(../ac/strip_show.m4)
|
||||
|
||||
|
@ -151,8 +153,10 @@ INSTALL_SETUP_RACKET_FLAGS=
|
|||
|
||||
Z_LIB_DEP='$(OWN_Z_LIB)'
|
||||
Z_LIB='$(OWN_Z_LIB)'
|
||||
Z_LIB_UNPACK='$(AR) x $(OWN_Z_LIB)'
|
||||
LZ4_LIB_DEP='$(OWN_LZ4_LIB)'
|
||||
LZ4_LIB='$(OWN_LZ4_LIB)'
|
||||
LZ4_LIB_UNPACK='$(AR) x $(OWN_LZ4_LIB)'
|
||||
|
||||
enable_pthread_by_default=yes
|
||||
|
||||
|
@ -249,6 +253,10 @@ case "$host_os" in
|
|||
if `which ${host}-windres > /dev/null` ; then
|
||||
WINDRES="${host}-windres"
|
||||
fi
|
||||
# ".a" is typically not useful, since we always build a DLL:
|
||||
if test "${enable_libs}" = "" ; then
|
||||
INSTALL_LIBS_ENABLE=no-install
|
||||
fi
|
||||
;;
|
||||
cygwin*)
|
||||
;;
|
||||
|
@ -542,6 +550,7 @@ if test "${enable_libz}" = "yes" ; then
|
|||
else
|
||||
Z_LIB_DEP=""
|
||||
Z_LIB="-lz"
|
||||
Z_LIB_UNPACK="$(NOOP)"
|
||||
extra_scheme_config_args="${extra_scheme_config_args} ZLIB=-lz"
|
||||
fi
|
||||
fi
|
||||
|
@ -563,6 +572,7 @@ if test "${enable_liblz4}" = "yes" ; then
|
|||
else
|
||||
LZ4_LIB_DEP=""
|
||||
LZ4_LIB="-llz4"
|
||||
LZ4_LIB_UNPACK="$(NOOP)"
|
||||
extra_scheme_config_args="${extra_scheme_config_args} LZ4=-llz4"
|
||||
fi
|
||||
fi
|
||||
|
@ -685,6 +695,7 @@ AC_SUBST(RANLIB)
|
|||
AC_SUBST(STATIC_AR)
|
||||
AC_SUBST(WINDRES)
|
||||
AC_SUBST(ICP)
|
||||
AC_SUBST(ICP_LIB)
|
||||
AC_SUBST(STRIP_DEBUG)
|
||||
AC_SUBST(STRIP_LIB_DEBUG)
|
||||
AC_SUBST(RKTLINKER)
|
||||
|
@ -707,8 +718,10 @@ AC_SUBST(MINGW)
|
|||
AC_SUBST(NOT_MINGW)
|
||||
AC_SUBST(Z_LIB_DEP)
|
||||
AC_SUBST(Z_LIB)
|
||||
AC_SUBST(Z_LIB_UNPACK)
|
||||
AC_SUBST(LZ4_LIB_DEP)
|
||||
AC_SUBST(LZ4_LIB)
|
||||
AC_SUBST(LZ4_LIB_UNPACK)
|
||||
AC_SUBST(CONFIGURE_RACKET_SO_COMPILE)
|
||||
AC_SUBST(COMPRESS_COMP)
|
||||
AC_SUBST(BOOT_COMPRESS_COMP)
|
||||
|
@ -727,6 +740,7 @@ AC_SUBST(CROSS_COMPILE_TARGET_KIND)
|
|||
AC_SUBST(RUN_RACKET)
|
||||
AC_SUBST(INSTALL_SETUP_FLAGS)
|
||||
AC_SUBST(INSTALL_SETUP_RACKET_FLAGS)
|
||||
AC_SUBST(INSTALL_LIBS_ENABLE)
|
||||
|
||||
makefiles="Makefile"
|
||||
|
||||
|
|
|
@ -48,8 +48,8 @@
|
|||
(if (compress-enabled?)
|
||||
;; zero byte stops a gzip-read sequence
|
||||
#"\0"
|
||||
;; #!eof encoding stops(!) a fasl-read sequence
|
||||
#"\44\26\2\f6"))
|
||||
;; A 127 byte teriminates a fasl-read sequence
|
||||
#"\177"))
|
||||
(define data
|
||||
(bytes-append bstr1 terminator
|
||||
bstr2 terminator
|
||||
|
|
|
@ -107,6 +107,45 @@ static long find_rktboot_section(char *me)
|
|||
}
|
||||
#endif
|
||||
|
||||
#if defined(OS_X) && !defined(RACKET_XONX)
|
||||
|
||||
# include <mach-o/dyld.h>
|
||||
# define RACKET_USE_FRAMEWORK 1
|
||||
|
||||
static const char *get_framework_path() {
|
||||
int i, c, len;
|
||||
const char *s;
|
||||
|
||||
c = _dyld_image_count();
|
||||
for (i = 0; i < c; i++) {
|
||||
s = _dyld_get_image_name(i);
|
||||
len = strlen(s);
|
||||
if ((len > 7) && !strcmp("/Racket", s + len - 7)) {
|
||||
char *s2;
|
||||
s2 = strdup(s);
|
||||
strcpy(s2 + len - 6, "boot");
|
||||
return s2;
|
||||
}
|
||||
}
|
||||
|
||||
return "???";
|
||||
}
|
||||
|
||||
static char *path_append(const char *p1, char *p2) {
|
||||
int l1, l2;
|
||||
char *s;
|
||||
l1 = strlen(p1);
|
||||
l2 = strlen(p2);
|
||||
s = malloc(l1 + l2 + 2);
|
||||
memcpy(s, p1, l1);
|
||||
s[l1] = '/';
|
||||
memcpy(s + l1 + 1, p2, l2);
|
||||
s[l1+l2+1] = 0;
|
||||
return s;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if defined(__linux__)
|
||||
# include <errno.h>
|
||||
static char *get_self_path(char *exec_file)
|
||||
|
@ -375,8 +414,13 @@ static int bytes_main(int argc, char **argv,
|
|||
/* for Windows and X11 GUI modes */
|
||||
int wm_is_gracket_or_x11_arg_count, char *gracket_guid_or_x11_args)
|
||||
{
|
||||
char *boot_exe, *exec_file = argv[0], *run_file = NULL;
|
||||
int is_embedded = 1, pos1, pos2, pos3;
|
||||
char *boot_exe;
|
||||
char *exec_file = argv[0], *run_file = NULL;
|
||||
char *boot1_path, *boot2_path, *boot3_path;
|
||||
int boot1_offset, boot2_offset, boot3_offset;
|
||||
#ifdef OS_X
|
||||
int boot_images_in_exe = 1;
|
||||
#endif
|
||||
long boot_offset;
|
||||
long segment_offset;
|
||||
#ifdef WIN32
|
||||
|
@ -392,6 +436,16 @@ static int bytes_main(int argc, char **argv,
|
|||
argv++;
|
||||
}
|
||||
|
||||
extract_built_in_arguments(&exec_file, &run_file, &argc, &argv);
|
||||
if (!run_file)
|
||||
run_file = exec_file;
|
||||
|
||||
segment_offset = get_segment_offset();
|
||||
|
||||
memcpy(&boot1_offset, boot_file_data + boot_file_offset, sizeof(boot1_offset));
|
||||
memcpy(&boot2_offset, boot_file_data + boot_file_offset + 4, sizeof(boot2_offset));
|
||||
memcpy(&boot3_offset, boot_file_data + boot_file_offset + 8, sizeof(boot3_offset));
|
||||
|
||||
#ifdef WIN32
|
||||
parse_embedded_dlls();
|
||||
register_embedded_dll_hooks();
|
||||
|
@ -412,39 +466,70 @@ static int bytes_main(int argc, char **argv,
|
|||
boot_exe = get_self_path(exec_file);
|
||||
#endif
|
||||
|
||||
extract_built_in_arguments(&exec_file, &run_file, &argc, &argv);
|
||||
if (!run_file)
|
||||
run_file = exec_file;
|
||||
|
||||
segment_offset = get_segment_offset();
|
||||
|
||||
memcpy(&pos1, boot_file_data + boot_file_offset, sizeof(pos1));
|
||||
memcpy(&pos2, boot_file_data + boot_file_offset + 4, sizeof(pos2));
|
||||
memcpy(&pos3, boot_file_data + boot_file_offset + 8, sizeof(pos2));
|
||||
|
||||
#ifdef ELF_FIND_BOOT_SECTION
|
||||
boot_offset = find_boot_section(boot_exe);
|
||||
#elif OS_X
|
||||
#elif defined(OS_X)
|
||||
boot_offset = find_rktboot_section(boot_exe);
|
||||
if (!boot_offset) is_embedded = 0;
|
||||
if (!boot_offset) boot_images_in_exe = 0;
|
||||
#elif WIN32
|
||||
boot_offset = find_resource_offset(dll_path, 259, boot_rsrc_offset);
|
||||
#else
|
||||
boot_offset = 0;
|
||||
#endif
|
||||
|
||||
pos1 += boot_offset;
|
||||
pos2 += boot_offset;
|
||||
pos3 += boot_offset;
|
||||
boot1_offset += boot_offset;
|
||||
boot2_offset += boot_offset;
|
||||
boot3_offset += boot_offset;
|
||||
|
||||
boot1_path = boot2_path = boot3_path = boot_exe;
|
||||
|
||||
#if defined(OS_X) && !defined(RACKET_XONX)
|
||||
if (!boot_images_in_exe) {
|
||||
const char *fw_path = get_framework_path();
|
||||
boot1_path = path_append(fw_path, "petite.boot");
|
||||
boot2_path = path_append(fw_path, "scheme.boot");
|
||||
boot3_path = path_append(fw_path, "racket.boot");
|
||||
boot1_offset = boot2_offset = boot3_offset = 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
{
|
||||
racket_boot_arguments_t ba;
|
||||
|
||||
memset(&ba, 0, sizeof(ba));
|
||||
|
||||
ba.boot1_path = boot1_path;
|
||||
ba.boot1_offset = boot1_offset;
|
||||
ba.boot2_path = boot2_path;
|
||||
ba.boot2_offset = boot2_offset;
|
||||
ba.boot3_path = boot3_path;
|
||||
ba.boot3_offset = boot3_offset;
|
||||
|
||||
ba.argc = argc;
|
||||
ba.argv = argv;
|
||||
ba.exec_file = exec_file;
|
||||
ba.run_file = run_file;
|
||||
ba.collects_dir = extract_coldir();
|
||||
ba.config_dir = extract_configdir();
|
||||
ba.dll_dir = extract_dlldir();
|
||||
|
||||
ba.cs_compiled_subdir = CS_COMPILED_SUBDIR;
|
||||
|
||||
ba.segment_offset = segment_offset;
|
||||
|
||||
ba.dll_open = embedded_dll_open;
|
||||
ba.dll_find_object = scheme_dll_find_object;
|
||||
ba.dll_close = embedded_dll_close;
|
||||
|
||||
ba.exit_after = 1;
|
||||
|
||||
ba.is_gui = RACKET_IS_GUI;
|
||||
ba.wm_is_gracket_or_x11_arg_count = wm_is_gracket_or_x11_arg_count;
|
||||
ba.gracket_guid_or_x11_args = gracket_guid_or_x11_args;
|
||||
|
||||
racket_boot(&ba);
|
||||
}
|
||||
|
||||
racket_boot(argc, argv, exec_file, run_file,
|
||||
boot_exe, segment_offset,
|
||||
extract_coldir(), extract_configdir(), extract_dlldir(),
|
||||
is_embedded, pos1, pos2, pos3,
|
||||
CS_COMPILED_SUBDIR, RACKET_IS_GUI,
|
||||
wm_is_gracket_or_x11_arg_count, gracket_guid_or_x11_args,
|
||||
embedded_dll_open, scheme_dll_find_object, embedded_dll_close);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -46,7 +46,8 @@
|
|||
linklet-performance-report!
|
||||
current-compile-target-machine
|
||||
compile-target-machine?
|
||||
add-cross-compiler!))
|
||||
add-cross-compiler!
|
||||
primitive-lookup))
|
||||
|
||||
(linklet-performance-init!)
|
||||
(unless omit-debugging?
|
||||
|
@ -78,18 +79,20 @@
|
|||
(define (getenv-bytes str)
|
||||
(environment-variables-ref (current-environment-variables) (string->utf8 str)))
|
||||
|
||||
(define builtin-argc 9)
|
||||
(define builtin-argc 10)
|
||||
(seq
|
||||
(unless (>= (length the-command-line-arguments) builtin-argc)
|
||||
(error 'racket (string-append
|
||||
"expected `exec-file`, `run-file`, `collects`, and `etc` paths"
|
||||
"expected `embedded-interactive-mode?`,"
|
||||
" `exec-file`, `run-file`, `collects`, and `etc` paths"
|
||||
" plus `segment-offset`, `cs-compiled-subdir?`, `is-gui?`,"
|
||||
" `wm-is-gracket-or-x11-arg-count`, and `gracket-guid-or-x11-args`"
|
||||
" to start")))
|
||||
(set-exec-file! (->path (list-ref the-command-line-arguments/maybe-bytes 0)))
|
||||
(set-run-file! (->path (list-ref the-command-line-arguments/maybe-bytes 1))))
|
||||
(set-exec-file! (->path (list-ref the-command-line-arguments/maybe-bytes 1)))
|
||||
(set-run-file! (->path (list-ref the-command-line-arguments/maybe-bytes 2))))
|
||||
(define embedded-interactive-mode? (string=? "true" (list-ref the-command-line-arguments 0)))
|
||||
(define-values (init-collects-dir collects-pre-extra)
|
||||
(let ([s (list-ref the-command-line-arguments/maybe-bytes 2)])
|
||||
(let ([s (list-ref the-command-line-arguments/maybe-bytes 3)])
|
||||
(cond
|
||||
[(or (equal? s "")
|
||||
(equal? s '#vu8()))
|
||||
|
@ -99,12 +102,12 @@
|
|||
(values (->path (car s))
|
||||
(map ->path (cdr s))))])))
|
||||
(define init-config-dir (->path (or (getenv-bytes "PLTCONFIGDIR")
|
||||
(list-ref the-command-line-arguments/maybe-bytes 3))))
|
||||
(define segment-offset (#%string->number (list-ref the-command-line-arguments 4)))
|
||||
(define cs-compiled-subdir? (string=? "true" (list-ref the-command-line-arguments 5)))
|
||||
(define gracket? (string=? "true" (list-ref the-command-line-arguments 6)))
|
||||
(define wm-is-gracket-or-x11-arg-count (string->number (list-ref the-command-line-arguments 7)))
|
||||
(define gracket-guid-or-x11-args (list-ref the-command-line-arguments 8))
|
||||
(list-ref the-command-line-arguments/maybe-bytes 4))))
|
||||
(define segment-offset (#%string->number (list-ref the-command-line-arguments 5)))
|
||||
(define cs-compiled-subdir? (string=? "true" (list-ref the-command-line-arguments 6)))
|
||||
(define gracket? (string=? "true" (list-ref the-command-line-arguments 7)))
|
||||
(define wm-is-gracket-or-x11-arg-count (string->number (list-ref the-command-line-arguments 8)))
|
||||
(define gracket-guid-or-x11-args (list-ref the-command-line-arguments 9))
|
||||
|
||||
(seq
|
||||
(when (foreign-entry? "racket_exit")
|
||||
|
@ -146,7 +149,7 @@
|
|||
#f
|
||||
(machine-type)))
|
||||
(define compiled-roots-path-list-string (getenv "PLTCOMPILEDROOTS"))
|
||||
(define embedded-load-in-places #f)
|
||||
(define embedded-load-in-places '())
|
||||
|
||||
(define (see saw . args)
|
||||
(let loop ([saw saw] [args args])
|
||||
|
@ -410,7 +413,7 @@
|
|||
(set! loads
|
||||
(cons
|
||||
(lambda ()
|
||||
(set! embedded-load-in-places (list n m))
|
||||
(set! embedded-load-in-places (cons (list #f n m #f) embedded-load-in-places))
|
||||
(embedded-load n m #f #t)
|
||||
(embedded-load m p #f #f))
|
||||
loads)))
|
||||
|
@ -760,6 +763,44 @@
|
|||
(version))])
|
||||
(path-list-string->path-list s (list (build-path 'same)))))))
|
||||
|
||||
;; Called when Racket is embedded in a larger application:
|
||||
(define (register-embedded-entry-info! escape)
|
||||
(let ([resume-k #f]) ;; to get back to Racket thread; expects a thunk
|
||||
((call/cc ;; Scheme-level `call/cc` to escape Racket's thread-engine loop
|
||||
(lambda (init-resume-k)
|
||||
(set! resume-k init-resume-k)
|
||||
(set-top-level-value!
|
||||
'embedded-racket-entry-info
|
||||
;; A vector of specific functions:
|
||||
(vector
|
||||
;; Resume the main Racket thread to apply `proc` to `args`,
|
||||
;; and return a list of result values; no exception handling
|
||||
;; or other such protections
|
||||
(lambda (proc args)
|
||||
(call/cc ;; Scheme-level `call/cc` to escape engine loop
|
||||
(lambda (entry-point-k)
|
||||
(resume-k
|
||||
(lambda ()
|
||||
(let-values ([vals (apply proc args)])
|
||||
((call/cc
|
||||
(lambda (latest-resume-k)
|
||||
(set! resume-k init-resume-k)
|
||||
(entry-point-k vals))))))))))
|
||||
;; Functions that are useful to apply and that
|
||||
;; provide access to everything else:
|
||||
primitive-lookup
|
||||
eval
|
||||
dynamic-require
|
||||
namespace-require
|
||||
;; bstr as #f => use path, start, and end
|
||||
;; path as #f => find executable
|
||||
;; end as #f => use file size
|
||||
(lambda (path start end bstr as-predefined?)
|
||||
(embedded-load start end bstr as-predefined? path)
|
||||
(when as-predefined?
|
||||
(set! embedded-load-in-places (cons (list path start end bstr) embedded-load-in-places))))))
|
||||
(escape))))))
|
||||
|
||||
(set-make-place-ports+fds! make-place-ports+fds)
|
||||
|
||||
(set-start-place!
|
||||
|
@ -768,9 +809,11 @@
|
|||
(regexp-place-init!)
|
||||
(expander-place-init!)
|
||||
(initialize-place!)
|
||||
(when embedded-load-in-places
|
||||
(let-values ([(n m) (apply values embedded-load-in-places)])
|
||||
(embedded-load n m #f #t)))
|
||||
(let loop ([l (reverse embedded-load-in-places)])
|
||||
(unless (null? l)
|
||||
(let-values ([(path n m bstr) (apply values (car l))])
|
||||
(embedded-load n m bstr #t path))
|
||||
(loop (cdr l))))
|
||||
(lambda ()
|
||||
(let ([f (dynamic-require mod sym)])
|
||||
(f pch)))))
|
||||
|
@ -789,45 +832,53 @@
|
|||
|
||||
(when version?
|
||||
(display (banner)))
|
||||
(call-in-main-thread
|
||||
(lambda ()
|
||||
(initialize-place!)
|
||||
|
||||
(when init-library
|
||||
(namespace-require+ init-library))
|
||||
|
||||
(call-with-continuation-prompt
|
||||
(call/cc ; Chez Scheme's `call/cc`, used here to escape from the Racket-thread engine loop
|
||||
(lambda (entry-point-k)
|
||||
(call-in-main-thread
|
||||
(lambda ()
|
||||
(for-each (lambda (ld) (ld))
|
||||
(reverse loads)))
|
||||
(default-continuation-prompt-tag)
|
||||
;; If any load escapes, then set the exit value and
|
||||
;; stop running loads (but maybe continue with the REPL)
|
||||
(lambda (proc)
|
||||
(set! exit-value 1)
|
||||
;; Let the actual default handler report an arity mismatch, etc.
|
||||
(initialize-place!)
|
||||
|
||||
(when init-library
|
||||
(namespace-require+ init-library))
|
||||
|
||||
(call-with-continuation-prompt
|
||||
(lambda () (abort-current-continuation (default-continuation-prompt-tag) proc)))))
|
||||
(lambda ()
|
||||
(for-each (lambda (ld) (ld))
|
||||
(reverse loads)))
|
||||
(default-continuation-prompt-tag)
|
||||
;; If any load escapes, then set the exit value and
|
||||
;; stop running loads (but maybe continue with the REPL)
|
||||
(lambda (proc)
|
||||
(set! exit-value 1)
|
||||
;; Let the actual default handler report an arity mismatch, etc.
|
||||
(call-with-continuation-prompt
|
||||
(lambda () (abort-current-continuation (default-continuation-prompt-tag) proc)))))
|
||||
|
||||
(when repl?
|
||||
(set! exit-value 0)
|
||||
(when repl-init?
|
||||
(let ([m (get-repl-init-filename)])
|
||||
(when m
|
||||
(call-with-continuation-prompt
|
||||
(lambda () (dynamic-require m 0))
|
||||
(default-continuation-prompt-tag)
|
||||
(lambda args (set! exit-value 1))))))
|
||||
(|#%app| (if text-repl?
|
||||
(dynamic-require 'racket/base 'read-eval-print-loop)
|
||||
(dynamic-require 'racket/gui/init 'graphical-read-eval-print-loop)))
|
||||
(when text-repl?
|
||||
(newline)))
|
||||
|
||||
(when repl?
|
||||
(set! exit-value 0)
|
||||
(when repl-init?
|
||||
(let ([m (get-repl-init-filename)])
|
||||
(when m
|
||||
(call-with-continuation-prompt
|
||||
(lambda () (dynamic-require m 0))
|
||||
(default-continuation-prompt-tag)
|
||||
(lambda args (set! exit-value 1))))))
|
||||
(|#%app| (if text-repl?
|
||||
(dynamic-require 'racket/base 'read-eval-print-loop)
|
||||
(dynamic-require 'racket/gui/init 'graphical-read-eval-print-loop)))
|
||||
(when text-repl?
|
||||
(newline)))
|
||||
(when yield?
|
||||
(|#%app| (executable-yield-handler) exit-value))
|
||||
|
||||
(when yield?
|
||||
(|#%app| (executable-yield-handler) exit-value))
|
||||
|
||||
(exit exit-value))))
|
||||
(cond
|
||||
[embedded-interactive-mode?
|
||||
(register-embedded-entry-info!
|
||||
(lambda ()
|
||||
(entry-point-k exit-value)))]
|
||||
[else
|
||||
(exit exit-value)]))))))
|
||||
|
||||
(define the-command-line-arguments
|
||||
(or (and (top-level-bound? 'bytes-command-line-arguments)
|
||||
|
|
|
@ -41,14 +41,21 @@
|
|||
((current-load/use-compiled) p #f))
|
||||
|
||||
;; used for the -k command-line argument:
|
||||
(define (embedded-load start end str as-predefined?)
|
||||
(let* ([s (if str
|
||||
str
|
||||
(let* ([sp (find-system-path 'exec-file)]
|
||||
[exe (find-executable-path sp #f)]
|
||||
[start (or (string->number start) 0)]
|
||||
[end (or (string->number end) 0)])
|
||||
(with-input-from-file exe
|
||||
(define (embedded-load start end bstr as-predefined? [in-path #f])
|
||||
(let* ([s (if bstr
|
||||
bstr
|
||||
(let* ([path (cond
|
||||
[(bytes? in-path) (bytes->path in-path)]
|
||||
[(string? in-path) in-path]
|
||||
[else
|
||||
(find-executable-path (find-system-path 'exec-file) #f)])]
|
||||
[start (if (string? start)
|
||||
(or (string->number start) 0)
|
||||
start)]
|
||||
[end (if (string? end)
|
||||
(or (string->number end) 0)
|
||||
(or end (file-size path)))])
|
||||
(with-input-from-file path
|
||||
(lambda ()
|
||||
(file-position (current-input-port) start)
|
||||
(read-bytes (max 0 (- end start)))))))]
|
||||
|
|
|
@ -50,7 +50,7 @@ m4_include(../ac/natipkg_arg.m4)
|
|||
AC_ARG_ENABLE(shared, [ --enable-shared create shared libraries (ok, but not recommended)])
|
||||
AC_ARG_ENABLE(dynlib, [ --enable-dynlib same as --enable-shared])
|
||||
AC_ARG_ENABLE(lt, [ --enable-lt=<prog> use <prog> instead of libtool; disable to use bundled], LIBTOOLPROG="$enableval", enable_lt=default)
|
||||
AC_ARG_ENABLE(libs, [ --enable-libs install static libraries (enabled by default for Unix)])
|
||||
m4_include(../ac/instlib_arg.m4)
|
||||
|
||||
AC_ARG_ENABLE(libffi, [ --enable-libffi use installed libffi (enabled by default for Unix)], , enable_libffi=default)
|
||||
|
||||
|
@ -231,8 +231,7 @@ show_explicitly_enabled "${enable_jitframe}" "jitframe"
|
|||
show_explicitly_enabled "${enable_noopt}" "No-optimization" "Note that this mode is intended only for debugging purposes"
|
||||
m4_include(../ac/strip_show.m4)
|
||||
|
||||
show_explicitly_enabled "${enable_libs}" "Installation of static libraries (if any)"
|
||||
show_explicitly_disabled "${enable_libs}" "Installation of static libraries (if any)"
|
||||
m4_include(../ac/instlib.m4)
|
||||
|
||||
m4_include(../ac/sdk_show.m4)
|
||||
|
||||
|
@ -299,8 +298,6 @@ MAIN_VARIANT=3m
|
|||
INSTALL_SETUP_FLAGS=
|
||||
INSTALL_SETUP_RACKET_FLAGS=
|
||||
|
||||
INSTALL_LIBS_ENABLE=no-install
|
||||
|
||||
use_flag_pthread=yes
|
||||
use_flag_posix_pthread=no
|
||||
mzrt_needs_pthread=yes
|
||||
|
@ -539,11 +536,6 @@ if test "${enable_jit}" = "yes" ; then
|
|||
check_for_mprotect=yes
|
||||
fi
|
||||
|
||||
if test "${enable_libs}" != "no" ; then
|
||||
# Canceled for some platforms below:
|
||||
INSTALL_LIBS_ENABLE=install
|
||||
fi
|
||||
|
||||
############## platform tests ################
|
||||
|
||||
# for flags we don't want to use in config tests:
|
||||
|
|
|
@ -253,17 +253,20 @@
|
|||
"petite"
|
||||
"scheme")
|
||||
|
||||
(system*! (find-exe)
|
||||
"-O" "info@compiler/cm"
|
||||
"-l-" "setup" boot-mode "../setup-go.rkt" "..//build/compiled"
|
||||
"ignored" "../build/ignored.d"
|
||||
"../cs/c/embed-boot.rkt"
|
||||
"++exe" "../build/raw_racketcs.exe" (format "../../Racket~a.exe" cs-suffix)
|
||||
"++exe" "../build/raw_gracketcs.exe" (format "../../lib/GRacket~a.exe" cs-suffix)
|
||||
"../build/raw_libracketcs.dll" "../../lib/libracketcsxxxxxxx.dll"
|
||||
"../build/petite-v.boot"
|
||||
"../build/scheme-v.boot"
|
||||
"../build/racket-v.boot")
|
||||
(define (bootstrap-racket! . args)
|
||||
(apply system*! (find-exe)
|
||||
"-O" "info@compiler/cm"
|
||||
"-l-" "setup" boot-mode "../setup-go.rkt" "../build/compiled"
|
||||
"ignored" "../build/ignored.d"
|
||||
args))
|
||||
|
||||
(bootstrap-racket! "../cs/c/embed-boot.rkt"
|
||||
"++exe" "../build/raw_racketcs.exe" (format "../../Racket~a.exe" cs-suffix)
|
||||
"++exe" "../build/raw_gracketcs.exe" (format "../../lib/GRacket~a.exe" cs-suffix)
|
||||
"../build/raw_libracketcs.dll" "../../lib/libracketcsxxxxxxx.dll"
|
||||
"../build/petite-v.boot"
|
||||
"../build/scheme-v.boot"
|
||||
"../build/racket-v.boot")
|
||||
|
||||
(system*! "mt"
|
||||
"-manifest" "racket/racket.manifest"
|
||||
|
@ -325,3 +328,15 @@
|
|||
(format "../../lib/system~a.rktd" cs-suffix)
|
||||
machine
|
||||
"machine")
|
||||
|
||||
(bootstrap-racket! "../cs/c/add-terminator.rkt"
|
||||
"../build/petite-v.boot"
|
||||
"../../lib/petite.boot")
|
||||
|
||||
(bootstrap-racket! "../cs/c/add-terminator.rkt"
|
||||
"../build/scheme-v.boot"
|
||||
"../../lib/scheme.boot")
|
||||
|
||||
(bootstrap-racket! "../cs/c/add-terminator.rkt"
|
||||
"../build/racket-v.boot"
|
||||
"../../lib/racket.boot")
|
||||
|
|
Loading…
Reference in New Issue
Block a user