From: Noah Lavine <noah.b.lavine@gmail.com>
To: guile-devel@gnu.org
Subject: Storing JIT Code
Date: Sun, 18 Jul 2010 22:01:36 -0400 [thread overview]
Message-ID: <AANLkTim1XXhgA6gCJEA_wMmCqtj1ztcqmWgldDEyZyP7@mail.gmail.com> (raw)
[-- Attachment #1: Type: text/plain, Size: 2189 bytes --]
Hello,
Attached are some patches I made for storing JIT code associated with
objcode objects. These are based on some threads a few weeks ago in
which we discussed how to handle JIT code, with the eventual goal of
adding a JIT compiler to Guile (I'm working on it).
The goal is to have a piece of JIT code associated with each objcode
object. Another possibility would be to associate them with procedure
objects, but that was rejected because it would make the procedure
object 5 words long, which might mess up caching.
I've tried two ways to do this so far: putting the JIT code in a
struct scm_objcode and putting it in the SCM object that always wraps
one of those structs. I tried the first way first, but I hit problems
because strings of bytecode are expected to be valid C structs, and
adding a pointer would require leaving more space there, which would
leak abstractions. Therefore, these patches implement the second way.
(A possible third way would be to put the JIT code in a property.)
The first patch adds the extra slot to the SCM object and initializes
it to C's NULL. This required changing a few functions in objcode.c to
make the SCMs differently. Unfortunately, I also had to change all of
the statically-generated objcode objects in continuations.c,
control.c, gsubr.c, foreign.c, and smob.c, so the patch is quite long.
The second patch adds some infrastructure to the VM to call a dummy
JIT compiler, cache its results, and run the resulting code if any is
generated. I set up a return convention so that the JIT compiler can
fail to compile things and the VM will run as usual, which I think
will be useful while there is a partially-complete compiler. (Although
I'm not convinced I've chosen the best values for it. Currently a NULL
jitcode means we've never tried to compile, and an SCM_BOOL_F means we
tried and failed, and therefore won't try again. Are there better
choices?)
I'm afraid these patches will require the set of small fixes I just
emailed, because one of the diffs modifies a comment that was added in
one of those patches. I believe the first patch is complete, but the
second patch is quite rough still. What do you think of them?
Noah
[-- Attachment #2: 0001-Add-JIT-pointers.patch --]
[-- Type: application/octet-stream, Size: 40413 bytes --]
From fde14a0a21c688978093c789899bd831f7ceb2da Mon Sep 17 00:00:00 2001
From: Noah Lavine <nlavine@haverford.edu>
Date: Sun, 18 Jul 2010 13:30:53 -0400
Subject: [PATCH] Add JIT pointers
Add a fifth machine word to the SCM objects that hold struct scm_objcodes to
store JIT code corresponding to that object code, and initialize them to
NULL.
---
libguile/continuations.c | 3 +-
libguile/control.c | 3 +-
libguile/foreign.c | 52 ++++---
libguile/gsubr.c | 374 ++++++++++++++++++++++++++++++---------------
libguile/objcodes.c | 37 ++++--
libguile/objcodes.h | 2 +
libguile/smob.c | 47 ++++--
7 files changed, 345 insertions(+), 173 deletions(-)
diff --git a/libguile/continuations.c b/libguile/continuations.c
index ed476a8..e9974e1 100644
--- a/libguile/continuations.c
+++ b/libguile/continuations.c
@@ -98,7 +98,8 @@ static const type sym##__unaligned[]
SCM_DECLARE_STATIC_ALIGNED_ARRAY (scm_t_uint8, sym##__bytecode); \
SCM_STATIC_ALIGNED_ARRAY (8, scm_t_cell, sym##__cells) = { \
{ STATIC_OBJCODE_TAG, SCM_PACK (sym##__bytecode) }, \
- { SCM_BOOL_F, SCM_PACK (0) } \
+ { SCM_BOOL_F, SCM_PACK (0) }, \
+ { NULL } \
}; \
static const SCM sym = SCM_PACK (sym##__cells); \
SCM_STATIC_ALIGNED_ARRAY (8, scm_t_uint8, sym##__bytecode)
diff --git a/libguile/control.c b/libguile/control.c
index caf79eb..fca39ab 100644
--- a/libguile/control.c
+++ b/libguile/control.c
@@ -105,7 +105,8 @@ static const type sym##__unaligned[]
SCM_DECLARE_STATIC_ALIGNED_ARRAY (scm_t_uint8, sym##__bytecode); \
SCM_STATIC_ALIGNED_ARRAY (8, scm_t_cell, sym##__cells) = { \
{ STATIC_OBJCODE_TAG, SCM_PACK (sym##__bytecode) }, \
- { SCM_BOOL_F, SCM_PACK (0) } \
+ { SCM_BOOL_F, SCM_PACK (0) }, \
+ { NULL } \
}; \
static const SCM sym = SCM_PACK (sym##__cells); \
SCM_STATIC_ALIGNED_ARRAY (8, scm_t_uint8, sym##__bytecode)
diff --git a/libguile/foreign.c b/libguile/foreign.c
index c541d13..6f68cba 100644
--- a/libguile/foreign.c
+++ b/libguile/foreign.c
@@ -788,20 +788,22 @@ static const struct
#undef CODE
#undef META
-#undef OBJCODE_HEADER
+/* don't undef OBJCODE_HEADER because the init function will use
+ * it to verify that it's the right size. */
#undef META_HEADER
/*
- (defun generate-objcode-cells (n)
- "Generate objcode cells for up to N arguments"
- (interactive "p")
- (let ((i 0))
- (while (< i n)
- (insert
- (format " { STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + %d) },\n"
- (* (+ 4 4 8 4 4 32) i)))
- (insert " { SCM_BOOL_F, SCM_PACK (0) },\n")
- (setq i (1+ i)))))
+(defun generate-objcode-cells (n)
+ "Generate objcode cells for up to N arguments"
+ (interactive "p")
+ (let ((i 0))
+ (while (< i n)
+ (insert
+ (format " { STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + %d) },\n"
+ (* (+ 4 4 8 4 4 32) i)))
+ (insert " { SCM_BOOL_F, SCM_PACK (0) },\n")
+ (insert " { NULL, 0 },\n")
+ (setq i (1+ i)))))
*/
#define STATIC_OBJCODE_TAG \
SCM_PACK (scm_tc7_objcode | (SCM_F_OBJCODE_IS_STATIC << 8))
@@ -809,45 +811,55 @@ static const struct
static const struct
{
scm_t_uint64 dummy; /* alignment */
- scm_t_cell cells[10 * 2]; /* 10 double cells */
+ scm_t_cell cells[10 * 3]; /* 10 six-word cells (last word unused) */
} objcode_cells = {
0,
/* C-u 1 0 M-x generate-objcode-cells RET */
- {
+ {
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 0) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 56) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 112) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 168) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 224) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 280) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 336) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 392) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 448) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 504) },
- { SCM_BOOL_F, SCM_PACK (0) }
+ { SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
}
};
static const SCM objcode_trampolines[10] = {
SCM_PACK (objcode_cells.cells+0),
- SCM_PACK (objcode_cells.cells+2),
- SCM_PACK (objcode_cells.cells+4),
+ SCM_PACK (objcode_cells.cells+3),
SCM_PACK (objcode_cells.cells+6),
- SCM_PACK (objcode_cells.cells+8),
- SCM_PACK (objcode_cells.cells+10),
+ SCM_PACK (objcode_cells.cells+9),
SCM_PACK (objcode_cells.cells+12),
- SCM_PACK (objcode_cells.cells+14),
- SCM_PACK (objcode_cells.cells+16),
+ SCM_PACK (objcode_cells.cells+15),
SCM_PACK (objcode_cells.cells+18),
+ SCM_PACK (objcode_cells.cells+21),
+ SCM_PACK (objcode_cells.cells+24),
+ SCM_PACK (objcode_cells.cells+27),
};
static SCM
diff --git a/libguile/gsubr.c b/libguile/gsubr.c
index af1c031..ceaddc6 100644
--- a/libguile/gsubr.c
+++ b/libguile/gsubr.c
@@ -274,36 +274,39 @@ static const struct
#undef AC
#undef BC
#undef ABC
-#undef OBJCODE_HEADER
+/* don't undef OBJCODE_HEADER because scm_init_gsubr will use it to verify
+ * that its size is correct. */
#undef META_HEADER
#undef META
/*
;; (nargs * nargs) + nopt + rest * (nargs + 1)
- (defun generate-objcode-cells-helper (n)
- "Generate objcode cells for N arguments"
- (interactive "p")
- (insert (format " /\* %d arguments *\/\n" n))
- (let ((nreq n))
- (while (<= 0 nreq)
- (let ((nopt (- n nreq)))
- (insert
- (format " { STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + %d) },\n"
- (* (+ 4 4 16 4 4 32)
- (+ (* n n) nopt))))
- (insert " { SCM_BOOL_F, SCM_PACK (0) },\n")
- (setq nreq (1- nreq))))
- (insert "\n")
- (setq nreq (1- n))
- (while (<= 0 nreq)
- (let ((nopt (- n nreq 1)))
- (insert
- (format " { STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + %d) },\n"
- (* (+ 4 4 16 4 4 32)
- (+ (* n n) nopt n 1))))
- (insert " { SCM_BOOL_F, SCM_PACK (0) },\n")
- (setq nreq (1- nreq))))
- (insert "\n")))
+(defun generate-objcode-cells-helper (n)
+ "Generate objcode cells for N arguments"
+ (interactive "p")
+ (insert (format " /\* %d arguments *\/\n" n))
+ (let ((nreq n))
+ (while (<= 0 nreq)
+ (let ((nopt (- n nreq)))
+ (insert
+ (format " { STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + %d) },\n"
+ (* (+ 4 4 16 4 4 32)
+ (+ (* n n) nopt))))
+ (insert " { SCM_BOOL_F, SCM_PACK (0) },\n")
+ (insert " { NULL, 0 },\n")
+ (setq nreq (1- nreq))))
+ (insert "\n")
+ (setq nreq (1- n))
+ (while (<= 0 nreq)
+ (let ((nopt (- n nreq 1)))
+ (insert
+ (format " { STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + %d) },\n"
+ (* (+ 4 4 16 4 4 32)
+ (+ (* n n) nopt n 1))))
+ (insert " { SCM_BOOL_F, SCM_PACK (0) },\n")
+ (insert " { NULL, 0 },\n")
+ (setq nreq (1- nreq))))
+ (insert "\n")))
(defun generate-objcode-cells (n)
"Generate objcode cells for up to N arguments"
@@ -320,7 +323,7 @@ static const struct
static const struct
{
scm_t_uint64 dummy; /* alignment */
- scm_t_cell cells[121 * 2]; /* 11*11 double cells */
+ scm_t_cell cells[121 * 3]; /* 11*11 triple cells (last word unused) */
} objcode_cells = {
0,
/* C-u 1 0 M-x generate-objcode-cells RET */
@@ -328,277 +331,398 @@ static const struct
/* 0 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 0) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
/* 1 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 64) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 128) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 192) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
/* 2 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 256) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 320) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 384) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 448) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 512) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
/* 3 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 576) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 640) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 704) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 768) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 832) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 896) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 960) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
/* 4 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1024) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1088) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1152) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1216) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1280) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1344) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1408) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1472) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1536) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
/* 5 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1600) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1664) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1728) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1792) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1856) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1920) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 1984) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2048) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2112) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2176) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2240) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
/* 6 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2304) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2368) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2432) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2496) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2560) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2624) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2688) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2752) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2816) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2880) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 2944) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3008) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3072) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
/* 7 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3136) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3200) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3264) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3328) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3392) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3456) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3520) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3584) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3648) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3712) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3776) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3840) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3904) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 3968) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4032) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
/* 8 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4096) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4160) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4224) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4288) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4352) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4416) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4480) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4544) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4608) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4672) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4736) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4800) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4864) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4928) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 4992) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5056) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5120) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
/* 9 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5184) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5248) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5312) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5376) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5440) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5504) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5568) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5632) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5696) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5760) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5824) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5888) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 5952) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6016) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6080) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6144) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6208) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6272) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6336) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
/* 10 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6400) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6464) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6528) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6592) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6656) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6720) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6784) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6848) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6912) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 6976) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 7040) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 7104) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 7168) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 7232) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 7296) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 7360) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 7424) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 7488) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 7552) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 7616) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 7680) },
- { SCM_BOOL_F, SCM_PACK (0) }
+ { SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
}
};
@@ -609,7 +733,7 @@ static const struct
(insert (format " /\* %d arguments *\/\n" n))
(let ((i (* n n)))
(while (< i (* (1+ n) (1+ n)))
- (insert (format " SCM_PACK (objcode_cells.cells+%d),\n" (* i 2)))
+ (insert (format " SCM_PACK (objcode_cells.cells+%d),\n" (* i 3)))
(setq i (1+ i)))
(insert "\n")))
@@ -627,144 +751,144 @@ static const SCM scm_subr_objcode_trampolines[121] = {
SCM_PACK (objcode_cells.cells+0),
/* 1 arguments */
- SCM_PACK (objcode_cells.cells+2),
- SCM_PACK (objcode_cells.cells+4),
+ SCM_PACK (objcode_cells.cells+3),
SCM_PACK (objcode_cells.cells+6),
+ SCM_PACK (objcode_cells.cells+9),
/* 2 arguments */
- SCM_PACK (objcode_cells.cells+8),
- SCM_PACK (objcode_cells.cells+10),
SCM_PACK (objcode_cells.cells+12),
- SCM_PACK (objcode_cells.cells+14),
- SCM_PACK (objcode_cells.cells+16),
-
- /* 3 arguments */
+ SCM_PACK (objcode_cells.cells+15),
SCM_PACK (objcode_cells.cells+18),
- SCM_PACK (objcode_cells.cells+20),
- SCM_PACK (objcode_cells.cells+22),
+ SCM_PACK (objcode_cells.cells+21),
SCM_PACK (objcode_cells.cells+24),
- SCM_PACK (objcode_cells.cells+26),
- SCM_PACK (objcode_cells.cells+28),
- SCM_PACK (objcode_cells.cells+30),
- /* 4 arguments */
- SCM_PACK (objcode_cells.cells+32),
- SCM_PACK (objcode_cells.cells+34),
+ /* 3 arguments */
+ SCM_PACK (objcode_cells.cells+27),
+ SCM_PACK (objcode_cells.cells+30),
+ SCM_PACK (objcode_cells.cells+33),
SCM_PACK (objcode_cells.cells+36),
- SCM_PACK (objcode_cells.cells+38),
- SCM_PACK (objcode_cells.cells+40),
+ SCM_PACK (objcode_cells.cells+39),
SCM_PACK (objcode_cells.cells+42),
- SCM_PACK (objcode_cells.cells+44),
- SCM_PACK (objcode_cells.cells+46),
- SCM_PACK (objcode_cells.cells+48),
+ SCM_PACK (objcode_cells.cells+45),
- /* 5 arguments */
- SCM_PACK (objcode_cells.cells+50),
- SCM_PACK (objcode_cells.cells+52),
+ /* 4 arguments */
+ SCM_PACK (objcode_cells.cells+48),
+ SCM_PACK (objcode_cells.cells+51),
SCM_PACK (objcode_cells.cells+54),
- SCM_PACK (objcode_cells.cells+56),
- SCM_PACK (objcode_cells.cells+58),
+ SCM_PACK (objcode_cells.cells+57),
SCM_PACK (objcode_cells.cells+60),
- SCM_PACK (objcode_cells.cells+62),
- SCM_PACK (objcode_cells.cells+64),
+ SCM_PACK (objcode_cells.cells+63),
SCM_PACK (objcode_cells.cells+66),
- SCM_PACK (objcode_cells.cells+68),
- SCM_PACK (objcode_cells.cells+70),
-
- /* 6 arguments */
+ SCM_PACK (objcode_cells.cells+69),
SCM_PACK (objcode_cells.cells+72),
- SCM_PACK (objcode_cells.cells+74),
- SCM_PACK (objcode_cells.cells+76),
+
+ /* 5 arguments */
+ SCM_PACK (objcode_cells.cells+75),
SCM_PACK (objcode_cells.cells+78),
- SCM_PACK (objcode_cells.cells+80),
- SCM_PACK (objcode_cells.cells+82),
+ SCM_PACK (objcode_cells.cells+81),
SCM_PACK (objcode_cells.cells+84),
- SCM_PACK (objcode_cells.cells+86),
- SCM_PACK (objcode_cells.cells+88),
+ SCM_PACK (objcode_cells.cells+87),
SCM_PACK (objcode_cells.cells+90),
- SCM_PACK (objcode_cells.cells+92),
- SCM_PACK (objcode_cells.cells+94),
+ SCM_PACK (objcode_cells.cells+93),
SCM_PACK (objcode_cells.cells+96),
-
- /* 7 arguments */
- SCM_PACK (objcode_cells.cells+98),
- SCM_PACK (objcode_cells.cells+100),
+ SCM_PACK (objcode_cells.cells+99),
SCM_PACK (objcode_cells.cells+102),
- SCM_PACK (objcode_cells.cells+104),
- SCM_PACK (objcode_cells.cells+106),
+ SCM_PACK (objcode_cells.cells+105),
+
+ /* 6 arguments */
SCM_PACK (objcode_cells.cells+108),
- SCM_PACK (objcode_cells.cells+110),
- SCM_PACK (objcode_cells.cells+112),
+ SCM_PACK (objcode_cells.cells+111),
SCM_PACK (objcode_cells.cells+114),
- SCM_PACK (objcode_cells.cells+116),
- SCM_PACK (objcode_cells.cells+118),
+ SCM_PACK (objcode_cells.cells+117),
SCM_PACK (objcode_cells.cells+120),
- SCM_PACK (objcode_cells.cells+122),
- SCM_PACK (objcode_cells.cells+124),
+ SCM_PACK (objcode_cells.cells+123),
SCM_PACK (objcode_cells.cells+126),
-
- /* 8 arguments */
- SCM_PACK (objcode_cells.cells+128),
- SCM_PACK (objcode_cells.cells+130),
+ SCM_PACK (objcode_cells.cells+129),
SCM_PACK (objcode_cells.cells+132),
- SCM_PACK (objcode_cells.cells+134),
- SCM_PACK (objcode_cells.cells+136),
+ SCM_PACK (objcode_cells.cells+135),
SCM_PACK (objcode_cells.cells+138),
- SCM_PACK (objcode_cells.cells+140),
- SCM_PACK (objcode_cells.cells+142),
+ SCM_PACK (objcode_cells.cells+141),
SCM_PACK (objcode_cells.cells+144),
- SCM_PACK (objcode_cells.cells+146),
- SCM_PACK (objcode_cells.cells+148),
+
+ /* 7 arguments */
+ SCM_PACK (objcode_cells.cells+147),
SCM_PACK (objcode_cells.cells+150),
- SCM_PACK (objcode_cells.cells+152),
- SCM_PACK (objcode_cells.cells+154),
+ SCM_PACK (objcode_cells.cells+153),
SCM_PACK (objcode_cells.cells+156),
- SCM_PACK (objcode_cells.cells+158),
- SCM_PACK (objcode_cells.cells+160),
-
- /* 9 arguments */
+ SCM_PACK (objcode_cells.cells+159),
SCM_PACK (objcode_cells.cells+162),
- SCM_PACK (objcode_cells.cells+164),
- SCM_PACK (objcode_cells.cells+166),
+ SCM_PACK (objcode_cells.cells+165),
SCM_PACK (objcode_cells.cells+168),
- SCM_PACK (objcode_cells.cells+170),
- SCM_PACK (objcode_cells.cells+172),
+ SCM_PACK (objcode_cells.cells+171),
SCM_PACK (objcode_cells.cells+174),
- SCM_PACK (objcode_cells.cells+176),
- SCM_PACK (objcode_cells.cells+178),
+ SCM_PACK (objcode_cells.cells+177),
SCM_PACK (objcode_cells.cells+180),
- SCM_PACK (objcode_cells.cells+182),
- SCM_PACK (objcode_cells.cells+184),
+ SCM_PACK (objcode_cells.cells+183),
SCM_PACK (objcode_cells.cells+186),
- SCM_PACK (objcode_cells.cells+188),
- SCM_PACK (objcode_cells.cells+190),
+ SCM_PACK (objcode_cells.cells+189),
+
+ /* 8 arguments */
SCM_PACK (objcode_cells.cells+192),
- SCM_PACK (objcode_cells.cells+194),
- SCM_PACK (objcode_cells.cells+196),
+ SCM_PACK (objcode_cells.cells+195),
SCM_PACK (objcode_cells.cells+198),
-
- /* 10 arguments */
- SCM_PACK (objcode_cells.cells+200),
- SCM_PACK (objcode_cells.cells+202),
+ SCM_PACK (objcode_cells.cells+201),
SCM_PACK (objcode_cells.cells+204),
- SCM_PACK (objcode_cells.cells+206),
- SCM_PACK (objcode_cells.cells+208),
+ SCM_PACK (objcode_cells.cells+207),
SCM_PACK (objcode_cells.cells+210),
- SCM_PACK (objcode_cells.cells+212),
- SCM_PACK (objcode_cells.cells+214),
+ SCM_PACK (objcode_cells.cells+213),
SCM_PACK (objcode_cells.cells+216),
- SCM_PACK (objcode_cells.cells+218),
- SCM_PACK (objcode_cells.cells+220),
+ SCM_PACK (objcode_cells.cells+219),
SCM_PACK (objcode_cells.cells+222),
- SCM_PACK (objcode_cells.cells+224),
- SCM_PACK (objcode_cells.cells+226),
+ SCM_PACK (objcode_cells.cells+225),
SCM_PACK (objcode_cells.cells+228),
- SCM_PACK (objcode_cells.cells+230),
- SCM_PACK (objcode_cells.cells+232),
+ SCM_PACK (objcode_cells.cells+231),
SCM_PACK (objcode_cells.cells+234),
- SCM_PACK (objcode_cells.cells+236),
- SCM_PACK (objcode_cells.cells+238),
- SCM_PACK (objcode_cells.cells+240)
+ SCM_PACK (objcode_cells.cells+237),
+ SCM_PACK (objcode_cells.cells+240),
+
+ /* 9 arguments */
+ SCM_PACK (objcode_cells.cells+243),
+ SCM_PACK (objcode_cells.cells+246),
+ SCM_PACK (objcode_cells.cells+249),
+ SCM_PACK (objcode_cells.cells+252),
+ SCM_PACK (objcode_cells.cells+255),
+ SCM_PACK (objcode_cells.cells+258),
+ SCM_PACK (objcode_cells.cells+261),
+ SCM_PACK (objcode_cells.cells+264),
+ SCM_PACK (objcode_cells.cells+267),
+ SCM_PACK (objcode_cells.cells+270),
+ SCM_PACK (objcode_cells.cells+273),
+ SCM_PACK (objcode_cells.cells+276),
+ SCM_PACK (objcode_cells.cells+279),
+ SCM_PACK (objcode_cells.cells+282),
+ SCM_PACK (objcode_cells.cells+285),
+ SCM_PACK (objcode_cells.cells+288),
+ SCM_PACK (objcode_cells.cells+291),
+ SCM_PACK (objcode_cells.cells+294),
+ SCM_PACK (objcode_cells.cells+297),
+
+ /* 10 arguments */
+ SCM_PACK (objcode_cells.cells+300),
+ SCM_PACK (objcode_cells.cells+303),
+ SCM_PACK (objcode_cells.cells+306),
+ SCM_PACK (objcode_cells.cells+309),
+ SCM_PACK (objcode_cells.cells+312),
+ SCM_PACK (objcode_cells.cells+315),
+ SCM_PACK (objcode_cells.cells+318),
+ SCM_PACK (objcode_cells.cells+321),
+ SCM_PACK (objcode_cells.cells+324),
+ SCM_PACK (objcode_cells.cells+327),
+ SCM_PACK (objcode_cells.cells+330),
+ SCM_PACK (objcode_cells.cells+333),
+ SCM_PACK (objcode_cells.cells+336),
+ SCM_PACK (objcode_cells.cells+339),
+ SCM_PACK (objcode_cells.cells+342),
+ SCM_PACK (objcode_cells.cells+345),
+ SCM_PACK (objcode_cells.cells+348),
+ SCM_PACK (objcode_cells.cells+351),
+ SCM_PACK (objcode_cells.cells+354),
+ SCM_PACK (objcode_cells.cells+357),
+ SCM_PACK (objcode_cells.cells+360),
};
/* (nargs * nargs) + nopt + rest * (nargs + 1) */
diff --git a/libguile/objcodes.c b/libguile/objcodes.c
index 41a5990..767c0ac 100644
--- a/libguile/objcodes.c
+++ b/libguile/objcodes.c
@@ -44,11 +44,13 @@ verify (((sizeof (SCM_OBJCODE_COOKIE) - 1) & 7) == 0);
* Objcode type
*/
-/* an objcode SCM object is a four-word object containing
+/* an objcode SCM object is a five-word object containing
- scm_tc7_objcode | the flags for this objcode
- the struct scm_objcode C object
- the parent of this objcode, if this is a slice, or #f if none
- the file descriptor this objcode came from if this was mmaped, or 0 if none
+ - the JIT code for this object, NULL if we've never tried to JIT this,
+ and #f if we tried and failed.
*/
static SCM
@@ -97,10 +99,12 @@ make_objcode_by_mmap (int fd)
+ data->metalen)));
}
- sret = scm_double_cell (scm_tc7_objcode | (SCM_F_OBJCODE_IS_MMAP<<8),
- (scm_t_bits)(addr + strlen (SCM_OBJCODE_COOKIE)),
- SCM_UNPACK (SCM_BOOL_F),
- (scm_t_bits)fd);
+ sret = scm_words (scm_tc7_objcode | (SCM_F_OBJCODE_IS_MMAP<<8), 5);
+ SCM_GC_SET_CELL_WORD (sret, 1,
+ (scm_t_bits)(addr + strlen(SCM_OBJCODE_COOKIE)));
+ SCM_GC_SET_CELL_WORD (sret, 2, SCM_UNPACK (SCM_BOOL_F));
+ SCM_GC_SET_CELL_WORD (sret, 3, (scm_t_bits)fd);
+ SCM_GC_SET_CELL_WORD (sret, 4, (scm_t_bits)NULL);
/* FIXME: we leak ourselves and the file descriptor. but then again so does
dlopen(). */
@@ -114,6 +118,7 @@ scm_c_make_objcode_slice (SCM parent, const scm_t_uint8 *ptr)
{
const struct scm_objcode *data, *parent_data;
const scm_t_uint8 *parent_base;
+ SCM ret;
SCM_VALIDATE_OBJCODE (1, parent);
parent_data = SCM_OBJCODE_DATA (parent);
@@ -137,8 +142,12 @@ scm_c_make_objcode_slice (SCM parent, const scm_t_uint8 *ptr)
assert (SCM_C_OBJCODE_BASE (data) + data->len + data->metalen
<= parent_base + parent_data->len + parent_data->metalen);
- return scm_double_cell (scm_tc7_objcode | (SCM_F_OBJCODE_IS_SLICE<<8),
- (scm_t_bits)data, SCM_UNPACK (parent), 0);
+ ret = scm_words (scm_tc7_objcode, 5);
+ SCM_GC_SET_CELL_WORD (ret, 1, (scm_t_bits)data);
+ SCM_GC_SET_CELL_WORD (ret, 2, SCM_UNPACK (parent));
+ SCM_GC_SET_CELL_WORD (ret, 3, 0);
+ SCM_GC_SET_CELL_WORD (ret, 4, NULL);
+ return ret;
}
#undef FUNC_NAME
@@ -179,7 +188,8 @@ SCM_DEFINE (scm_bytecode_to_objcode, "bytecode->objcode", 1, 0, 0,
size_t size;
const scm_t_uint8 *c_bytecode;
struct scm_objcode *data;
-
+ SCM ret;
+
if (!scm_is_bytevector (bytecode))
scm_wrong_type_arg (FUNC_NAME, 1, bytecode);
@@ -187,17 +197,22 @@ SCM_DEFINE (scm_bytecode_to_objcode, "bytecode->objcode", 1, 0, 0,
c_bytecode = (const scm_t_uint8*)SCM_BYTEVECTOR_CONTENTS (bytecode);
SCM_ASSERT_RANGE (0, bytecode, size >= sizeof(struct scm_objcode));
+
data = (struct scm_objcode*)c_bytecode;
if (data->len + data->metalen != (size - sizeof (*data)))
scm_misc_error (FUNC_NAME, "bad bytevector size (~a != ~a)",
scm_list_2 (scm_from_size_t (size),
scm_from_uint32 (sizeof (*data) + data->len + data->metalen)));
-
+
/* foolishly, we assume that as long as bytecode is around, that c_bytecode
will be of the same length; perhaps a bad assumption? */
- return scm_double_cell (scm_tc7_objcode | (SCM_F_OBJCODE_IS_BYTEVECTOR<<8),
- (scm_t_bits)data, SCM_UNPACK (bytecode), 0);
+ ret = scm_words (scm_tc7_objcode | (SCM_F_OBJCODE_IS_BYTEVECTOR<<8), 5);
+ SCM_GC_SET_CELL_WORD (ret, 1, (scm_t_bits)data);
+ SCM_GC_SET_CELL_WORD (ret, 2, SCM_UNPACK (bytecode));
+ SCM_GC_SET_CELL_WORD (ret, 3, 0);
+ SCM_GC_SET_CELL_WORD (ret, 4, NULL);
+ return ret;
}
#undef FUNC_NAME
diff --git a/libguile/objcodes.h b/libguile/objcodes.h
index 2bff9aa..b92e8ef 100644
--- a/libguile/objcodes.h
+++ b/libguile/objcodes.h
@@ -54,6 +54,8 @@ struct scm_objcode
#define SCM_OBJCODE_IS_BYTEVECTOR(x) (SCM_OBJCODE_FLAGS (x) & SCM_F_OBJCODE_IS_BYTEVECTOR)
#define SCM_OBJCODE_IS_SLICE(x) (SCM_OBJCODE_FLAGS (x) & SCM_F_OBJCODE_IS_SLICE)
+#define SCM_OBJCODE_JITCODE(x) (SCM_CELL_WORD ((x), 4))
+
SCM scm_c_make_objcode_slice (SCM parent, const scm_t_uint8 *ptr);
SCM_API SCM scm_load_objcode (SCM file);
SCM_API SCM scm_objcode_p (SCM obj);
diff --git a/libguile/smob.c b/libguile/smob.c
index 6582612..7d8abb2 100644
--- a/libguile/smob.c
+++ b/libguile/smob.c
@@ -261,7 +261,7 @@ static const struct
static const struct
{
scm_t_uint64 dummy; /* alignment */
- scm_t_cell cells[16 * 2]; /* 4*4 double cells */
+ scm_t_cell cells[16 * 3]; /* 4*4 triple cells (last cell unused) */
} objcode_cells = {
0,
/* C-u 3 M-x generate-objcode-cells RET */
@@ -269,45 +269,62 @@ static const struct
/* 0 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 0) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
+
/* 1 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 64) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 128) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 192) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
/* 2 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 256) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 320) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 384) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 448) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 512) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
/* 3 arguments */
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 576) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 640) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 704) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 768) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 832) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 896) },
{ SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
{ STATIC_OBJCODE_TAG, SCM_PACK (raw_bytecode.bytes + 960) },
- { SCM_BOOL_F, SCM_PACK (0) }
+ { SCM_BOOL_F, SCM_PACK (0) },
+ { NULL, 0 },
}
};
@@ -317,25 +334,25 @@ static const SCM scm_smob_objcode_trampolines[16] = {
SCM_PACK (objcode_cells.cells+0),
/* 1 arguments */
- SCM_PACK (objcode_cells.cells+2),
- SCM_PACK (objcode_cells.cells+4),
+ SCM_PACK (objcode_cells.cells+3),
SCM_PACK (objcode_cells.cells+6),
+ SCM_PACK (objcode_cells.cells+9),
/* 2 arguments */
- SCM_PACK (objcode_cells.cells+8),
- SCM_PACK (objcode_cells.cells+10),
SCM_PACK (objcode_cells.cells+12),
- SCM_PACK (objcode_cells.cells+14),
- SCM_PACK (objcode_cells.cells+16),
-
- /* 3 arguments */
+ SCM_PACK (objcode_cells.cells+15),
SCM_PACK (objcode_cells.cells+18),
- SCM_PACK (objcode_cells.cells+20),
- SCM_PACK (objcode_cells.cells+22),
+ SCM_PACK (objcode_cells.cells+21),
SCM_PACK (objcode_cells.cells+24),
- SCM_PACK (objcode_cells.cells+26),
- SCM_PACK (objcode_cells.cells+28),
- SCM_PACK (objcode_cells.cells+30)
+
+ /* 3 arguments */
+ SCM_PACK (objcode_cells.cells+27),
+ SCM_PACK (objcode_cells.cells+30),
+ SCM_PACK (objcode_cells.cells+33),
+ SCM_PACK (objcode_cells.cells+36),
+ SCM_PACK (objcode_cells.cells+39),
+ SCM_PACK (objcode_cells.cells+42),
+ SCM_PACK (objcode_cells.cells+45),
};
/* (nargs * nargs) + nopt + rest * (nargs + 1) */
--
1.7.1
[-- Attachment #3: 0002-Add-JIT-Infrastructure.patch --]
[-- Type: application/octet-stream, Size: 8670 bytes --]
From 10d47c5561917eb0b9b7fc5a3ef0154ff38925fc Mon Sep 17 00:00:00 2001
From: Noah Lavine <nlavine@haverford.edu>
Date: Sun, 18 Jul 2010 13:35:27 -0400
Subject: [PATCH] Add JIT Infrastructure
Add a dummy JIT compiler, and the infrastructure to invoke it on object code,
run the JIT code if it's generated, and cache the JIT code for future use.
---
libguile/Makefile.am | 2 +
libguile/init.c | 4 ++-
libguile/vm-engine.c | 22 ++++++++++++++++-
libguile/vm-engine.h | 2 +
libguile/vm-i-system.c | 17 +++++++++++++
libguile/vm-jit.c | 60 ++++++++++++++++++++++++++++++++++++++++++++++++
libguile/vm-jit.h | 39 +++++++++++++++++++++++++++++++
7 files changed, 144 insertions(+), 2 deletions(-)
create mode 100644 libguile/vm-jit.c
create mode 100644 libguile/vm-jit.h
diff --git a/libguile/Makefile.am b/libguile/Makefile.am
index 5eea8dc..3da0009 100644
--- a/libguile/Makefile.am
+++ b/libguile/Makefile.am
@@ -210,6 +210,7 @@ libguile_@GUILE_EFFECTIVE_VERSION@_la_SOURCES = \
vectors.c \
version.c \
vm.c \
+ vm-jit.c \
vports.c \
weaks.c
@@ -583,6 +584,7 @@ modinclude_HEADERS = \
vectors.h \
vm-engine.h \
vm-expand.h \
+ vm-jit.h \
vm.h \
vports.h \
weaks.h
diff --git a/libguile/init.c b/libguile/init.c
index 4843910..7c88a4a 100644
--- a/libguile/init.c
+++ b/libguile/init.c
@@ -128,6 +128,7 @@
#include "libguile/vectors.h"
#include "libguile/version.h"
#include "libguile/vm.h"
+#include "libguile/vm-jit.h"
#include "libguile/vports.h"
#include "libguile/weaks.h"
#include "libguile/guardians.h"
@@ -546,7 +547,8 @@ scm_i_init_guile (SCM_STACKITEM *base)
scm_init_weaks ();
scm_init_guardians (); /* requires smob_prehistory */
scm_init_vports ();
- scm_init_standard_ports (); /* Requires fports */
+ scm_init_jit ();
+ scm_init_standard_ports (); /* Requires fports, jit */
scm_init_expand (); /* Requires structs */
scm_init_memoize (); /* Requires smob_prehistory */
scm_init_eval (); /* Requires smob_prehistory */
diff --git a/libguile/vm-engine.c b/libguile/vm-engine.c
index 7f4641a..a567a85 100644
--- a/libguile/vm-engine.c
+++ b/libguile/vm-engine.c
@@ -31,7 +31,7 @@
#endif
#include "vm-engine.h"
-
+#include "tags.h" /* for SCM_BOOL_F */
static SCM
VM_NAME (SCM vm, SCM program, SCM *argv, int nargs)
@@ -47,6 +47,7 @@ VM_NAME (SCM vm, SCM program, SCM *argv, int nargs)
SCM *objects = NULL; /* constant objects */
size_t object_count = 0; /* length of OBJECTS */
SCM *stack_limit = vp->stack_limit; /* stack limit address */
+ jitf *jitcode = NULL; /* JIT code, if any */
SCM dynstate = SCM_I_CURRENT_THREAD->dynamic_state;
scm_t_int64 vm_cookie = vp->cookie++;
@@ -80,6 +81,10 @@ VM_NAME (SCM vm, SCM program, SCM *argv, int nargs)
{
SCM prog = program;
+ /* program could also be a smob. maybe other things? */
+ if (SCM_PROGRAM_P(program))
+ jitcode = (jitf *)SCM_OBJCODE_JITCODE(SCM_PROGRAM_OBJCODE(program));
+
/* Boot program */
program = vm_make_boot_program (nargs);
@@ -105,6 +110,21 @@ VM_NAME (SCM vm, SCM program, SCM *argv, int nargs)
/* Let's go! */
BOOT_HOOK ();
+
+ if (jitcode == NULL) {
+ jitcode = jit_objcode(bp);
+ SCM_OBJCODE_JITCODE(SCM_PROGRAM_OBJCODE(program)) = jitcode;
+ }
+ if (jitcode != SCM_BOOL_F) {
+ scm_t_uint8 *sip = ip;
+ SCM *ssp = sp;
+ SCM *sfp = fp;
+ SCM_JITCODE_ENTER(jitcode, sip, ssp, sfp);
+ ip = sip;
+ sp = ssp;
+ fp = sfp;
+ }
+ /* if the jitcode runs, we'll still want to do NEXT afterwards */
NEXT;
#ifndef HAVE_LABELS_AS_VALUES
diff --git a/libguile/vm-engine.h b/libguile/vm-engine.h
index 836648c..b90e481 100644
--- a/libguile/vm-engine.h
+++ b/libguile/vm-engine.h
@@ -90,6 +90,8 @@
#define FP_REG
#endif
+#include "vm-jit.h"
+
\f
/*
* Cache/Sync
diff --git a/libguile/vm-i-system.c b/libguile/vm-i-system.c
index 11f8ae0..5499bcf 100644
--- a/libguile/vm-i-system.c
+++ b/libguile/vm-i-system.c
@@ -744,6 +744,7 @@ VM_DEFINE_INSTRUCTION (53, new_frame, "new-frame", 0, 0, 3)
VM_DEFINE_INSTRUCTION (54, call, "call", 1, -1, 1)
{
+ (jitf *)jitcode = NULL;
nargs = FETCH ();
vm_call:
@@ -778,6 +779,22 @@ VM_DEFINE_INSTRUCTION (54, call, "call", 1, -1, 1)
ip = SCM_C_OBJCODE_BASE (bp);
ENTER_HOOK ();
APPLY_HOOK ();
+
+ jitcode = SCM_OBJCODE_JITCODE(SCM_PROGRAM_OBJCODE(program));
+ if (jitcode == NULL) {
+ jitcode = jit_objcode(bp);
+ SCM_OBJCODE_JITCODE(SCM_PROGRAM_OBJCODE(program)) = jitcode;
+ }
+ if (jitcode != SCM_BOOL_F) {
+ scm_t_uint8 *sip = ip;
+ SCM *ssp = sp;
+ SCM *sfp = fp;
+ SCM_JITCODE_ENTER(jitcode, sip, ssp, sfp);
+ ip = sip;
+ sp = ssp;
+ fp = sfp;
+ }
+ /* if the jitcode runs, we'll still want to do NEXT afterwards */
NEXT;
}
diff --git a/libguile/vm-jit.c b/libguile/vm-jit.c
new file mode 100644
index 0000000..d9a4a08
--- /dev/null
+++ b/libguile/vm-jit.c
@@ -0,0 +1,60 @@
+#include <stdio.h>
+
+#include "libguile/instructions.h"
+#include "libguile/snarf.h"
+#include "libguile/objcodes.h"
+#include "libguile/symbols.h"
+#include "libguile/list.h"
+#include "libguile/tags.h"
+#include "libguile/strings.h" /* for scm_from_locale_string, for the init function */
+#include "libguile/struct.h"
+#include "libguile/numbers.h"
+
+#include "libguile/vm-jit.h" /* defines struct scm_jit_code */
+#include "lightning.h"
+
+/* SCM jitcode_vtable = NULL; */
+
+/* jit_objcode: this procedure either JITs the given object code, and returns a
+ * pointer to an scm_jit_code object with the results, or SCM_BOOL_F if it
+ * couldn't jit the code. this will most likely occur if the jitter hits an
+ * object code that it doesn't know how to translate. */
+jitf *jit_objcode(struct scm_objcode *objcode)
+{
+ /* SCM code; */
+ jitf *code;
+ jit_insn *buffer, *end;
+
+ buffer = scm_gc_calloc(32 * sizeof (jit_insn), "JIT instruction buffer");
+ if (buffer == NULL)
+ return (jitf *)SCM_BOOL_F;
+
+ /* Make a test function */
+ jit_set_ip(buffer);
+ jit_prolog(3);
+ jit_movi_p(JIT_R0, "JIT code called!\n");
+ jit_prepare(1);
+ jit_pusharg_p(JIT_R0);
+ jit_finish(printf);
+ jit_ret();
+
+ end = (jit_insn *)jit_get_ip().ptr;
+ jit_flush_code(buffer, end);
+
+ /* Make the struct */
+ /* code = scm_c_make_structv(jitcode_vtable, 1, 1, (scm_t_bits *)buffer); */
+ code = scm_gc_malloc (sizeof (jitf *), "a table of pointers to machine code");
+ if (code == NULL)
+ return (jitf *)SCM_BOOL_F;
+
+ *code = (jitf *)buffer;
+
+ return code;
+}
+
+void scm_init_jit (void)
+{
+ /* jitcode_vtable = scm_make_vtable (scm_from_locale_string("pO"), SCM_UNDEFINED); */
+
+ return;
+}
diff --git a/libguile/vm-jit.h b/libguile/vm-jit.h
new file mode 100644
index 0000000..8251fef
--- /dev/null
+++ b/libguile/vm-jit.h
@@ -0,0 +1,39 @@
+#ifndef _SCM_VM_JIT_H_
+#define _SCM_VM_JIT_H_
+
+#include "_scm.h"
+#include "libguile/struct.h"
+
+/* jitted code for a procedure will be stored as an array of pointers to the
+ * blocks of the machine code. the generated machine code will expect this array
+ * to be available (how?) when it is called, and all machine code branches will
+ * indirect through this array. this is done to make the code relocatable: as
+ * long as the block array points to the correct blocks, then the code can be
+ * loaded anywhere in memory. this is important because it will allow us to
+ * store the code to a .go file and mmap() it back into memory and have it still
+ * work, which will allow fast startups. if we're storing code for a procedure,
+ * the first pointer in the block array will point to the procedure entry point.
+ *
+ * a block is a basic block of the object code. it's not really a basic block
+ * from the JIT perspective, because all of the instructions are implemented as
+ * calls to C functions.
+ *
+ * (one could also implement position-independent code by only using relative
+ * branches, but it's not clear that GNU Lightning supports this, so I'll use
+ * the table method.) */
+
+typedef void (*jitf)(void *block_pointers, scm_t_uint8 **ip,
+ SCM **sp, SCM **fp);
+
+/* the first block is number 1. */
+#define SCM_C_JITCODE_BLOCK(block_pointers, n) \
+ (*((block_pointers) + (n) - 1))
+ /* SCM_STRUCT_SLOT_REF(obj, n - 1) */
+#define SCM_JITCODE_ENTER(obj, ip, sp, fp) \
+ ((jitf)(SCM_C_JITCODE_BLOCK(obj, 1)))(SCM_C_JITCODE_BLOCK(obj, 1), &ip, &sp, &fp)
+
+jitf *jit_objcode(struct scm_objcode *objcode);
+
+void scm_init_jit (void);
+
+#endif /* not _SCM_VM_JIT_H_ */
--
1.7.1
next reply other threads:[~2010-07-19 2:01 UTC|newest]
Thread overview: 3+ messages / expand[flat|nested] mbox.gz Atom feed top
2010-07-19 2:01 Noah Lavine [this message]
2010-08-19 5:58 ` Storing JIT Code Andy Wingo
2010-08-19 12:40 ` Noah Lavine
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
List information: https://www.gnu.org/software/guile/
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=AANLkTim1XXhgA6gCJEA_wMmCqtj1ztcqmWgldDEyZyP7@mail.gmail.com \
--to=noah.b.lavine@gmail.com \
--cc=guile-devel@gnu.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).