]> gitweb.factorcode.org Git - factor.git/commitdiff
Reorganising bootstrap files
authorBjörn Lindqvist <bjourne@gmail.com>
Sun, 17 May 2015 08:11:48 +0000 (10:11 +0200)
committerDoug Coleman <doug.coleman@gmail.com>
Fri, 22 May 2015 19:22:24 +0000 (12:22 -0700)
All the bootstrap.factor scripts in cpu/ are run by the bootstrap to
make boot images, but aren't used otherwise. So I think it's cleaner to
put them in one directory inside the bootstrap hierarchy.

31 files changed:
basis/bootstrap/assembler/ppc.32.linux.factor [new file with mode: 0644]
basis/bootstrap/assembler/ppc.64.linux.factor [new file with mode: 0644]
basis/bootstrap/assembler/ppc.factor [new file with mode: 0644]
basis/bootstrap/assembler/x86.32.factor [new file with mode: 0644]
basis/bootstrap/assembler/x86.32.unix.factor [new file with mode: 0644]
basis/bootstrap/assembler/x86.32.windows.factor [new file with mode: 0644]
basis/bootstrap/assembler/x86.64.factor [new file with mode: 0644]
basis/bootstrap/assembler/x86.64.unix.factor [new file with mode: 0644]
basis/bootstrap/assembler/x86.64.windows.factor [new file with mode: 0644]
basis/bootstrap/assembler/x86.factor [new file with mode: 0644]
basis/bootstrap/assembler/x86.unix.factor [new file with mode: 0644]
basis/bootstrap/assembler/x86.windows.factor [new file with mode: 0644]
basis/cpu/ppc/32/linux/bootstrap.factor [deleted file]
basis/cpu/ppc/64/linux/bootstrap.factor [deleted file]
basis/cpu/ppc/bootstrap.factor [deleted file]
basis/cpu/x86/32/bootstrap.factor [deleted file]
basis/cpu/x86/32/unix/bootstrap.factor [deleted file]
basis/cpu/x86/32/windows/bootstrap.factor [deleted file]
basis/cpu/x86/64/bootstrap.factor [deleted file]
basis/cpu/x86/64/unix/bootstrap.factor [deleted file]
basis/cpu/x86/64/windows/bootstrap.factor [deleted file]
basis/cpu/x86/bootstrap.factor [deleted file]
basis/cpu/x86/unix/bootstrap.factor [deleted file]
basis/cpu/x86/windows/bootstrap.factor [deleted file]
core/bootstrap/primitives.factor
vm/cpu-x86.32.hpp
vm/os-linux-x86.64.hpp
vm/os-macosx-x86.64.hpp
vm/os-windows-x86.32.cpp
vm/os-windows.64.hpp
vm/quotations.cpp

diff --git a/basis/bootstrap/assembler/ppc.32.linux.factor b/basis/bootstrap/assembler/ppc.32.linux.factor
new file mode 100644 (file)
index 0000000..a9f55b6
--- /dev/null
@@ -0,0 +1,73 @@
+! Copyright (C) 2011 Erik Charlebois.
+! See http://factorcode.org/license.txt for BSD license.
+USING: parser system kernel sequences math math.ranges
+cpu.ppc.assembler combinators compiler.constants
+bootstrap.image.private layouts namespaces ;
+IN: bootstrap.ppc
+
+4 \ cell set
+big-endian on
+
+: reserved-size ( -- n ) 24 ;
+: lr-save ( -- n ) 4 ;
+
+CONSTANT: ds-reg    14
+CONSTANT: rs-reg    15
+CONSTANT: vm-reg    16
+CONSTANT: ctx-reg   17
+CONSTANT: frame-reg 31
+: nv-int-regs ( -- seq ) 13 31 [a,b] ;
+
+: LOAD32 ( r n -- )
+    [ -16 shift 0xffff bitand LIS ]
+    [ [ dup ] dip 0xffff bitand ORI ] 2bi ;
+
+: jit-trap-null ( src -- ) drop ;
+: jit-load-vm ( dst -- )
+    0 LOAD32 0 rc-absolute-ppc-2/2 jit-vm ;
+: jit-load-dlsym ( dst string -- )
+    [ 0 LOAD32 ] dip rc-absolute-ppc-2/2 jit-dlsym ;
+: jit-load-dlsym-toc ( string -- ) drop ;
+: jit-load-vm-arg ( dst -- )
+    0 LOAD32 rc-absolute-ppc-2/2 rt-vm jit-rel ;
+: jit-load-entry-point-arg ( dst -- )
+    0 LOAD32 rc-absolute-ppc-2/2 rt-entry-point jit-rel ;
+: jit-load-this-arg ( dst -- )
+    0 LOAD32 rc-absolute-ppc-2/2 rt-this jit-rel ;
+: jit-load-literal-arg ( dst -- )
+    0 LOAD32 rc-absolute-ppc-2/2 rt-literal jit-rel ;
+: jit-load-dlsym-arg ( dst -- )
+    0 LOAD32 rc-absolute-ppc-2/2 rt-dlsym jit-rel ;
+: jit-load-dlsym-toc-arg ( -- ) ;
+: jit-load-here-arg ( dst -- )
+    0 LOAD32 rc-absolute-ppc-2/2 rt-here jit-rel ;
+: jit-load-megamorphic-cache-arg ( dst -- )
+    0 LOAD32 rc-absolute-ppc-2/2 rt-megamorphic-cache-hits jit-rel ;
+: jit-load-cell ( dst src offset -- ) LWZ ;
+: jit-load-cell-x ( dst src offset -- ) LWZX ;
+: jit-load-cell-update ( dst src offset -- ) LWZU ;
+: jit-save-cell ( dst src offset -- ) STW ;
+: jit-save-cell-x ( dst src offset -- ) STWX ;
+: jit-save-cell-update ( dst src offset -- ) STWU ;
+: jit-load-int ( dst src offset -- ) LWZ ;
+: jit-save-int ( dst src offset -- ) STW ;
+: jit-shift-tag-bits ( dst src -- ) tag-bits get SRAWI ;
+: jit-mask-tag-bits ( dst src -- ) tag-bits get CLRRWI ;
+: jit-shift-fixnum-slot ( dst src -- ) 2 SRAWI ;
+: jit-class-hashcode ( dst src -- ) 1 SRAWI ;
+: jit-shift-left-logical ( dst src n -- ) SLW ;
+: jit-shift-left-logical-imm ( dst src n -- ) SLWI ;
+: jit-shift-right-algebraic ( dst src n -- ) SRAW ;
+: jit-divide ( dst ra rb -- ) DIVW ;
+: jit-multiply-low ( dst ra rb -- ) MULLW ;
+: jit-multiply-low-ov-rc ( dst ra rb -- ) MULLWO. ;
+: jit-compare-cell ( cr ra rb -- ) CMPW ;
+: jit-compare-cell-imm ( cr ra imm -- ) CMPWI ;
+
+: cell-size ( -- n ) 4 ;
+: factor-area-size ( -- n ) 16 ;
+: param-size ( -- n ) 32 ;
+: saved-int-regs-size ( -- n ) 96 ;
+
+<< "vocab:bootstrap/assembler/ppc.factor" parse-file suffix! >>
+call
diff --git a/basis/bootstrap/assembler/ppc.64.linux.factor b/basis/bootstrap/assembler/ppc.64.linux.factor
new file mode 100644 (file)
index 0000000..831b95b
--- /dev/null
@@ -0,0 +1,80 @@
+! Copyright (C) 2011 Erik Charlebois.
+! See http://factorcode.org/license.txt for BSD license.
+USING: parser system kernel sequences math math.ranges
+cpu.ppc.assembler combinators compiler.constants
+bootstrap.image.private layouts namespaces ;
+IN: bootstrap.ppc
+
+8 \ cell set
+big-endian on
+
+: reserved-size ( -- n ) 48 ;
+: lr-save ( -- n ) 16 ;
+
+CONSTANT: ds-reg    14
+CONSTANT: rs-reg    15
+CONSTANT: vm-reg    16
+CONSTANT: ctx-reg   17
+CONSTANT: frame-reg 31
+: nv-int-regs ( -- seq ) 13 31 [a,b] ;
+
+: LOAD64 ( r n -- )
+    [ dup ] dip {
+        [ nip -48 shift 0xffff bitand LIS ]
+        [ -32 shift 0xffff bitand ORI ]
+        [ drop 32 SLDI ]
+        [ -16 shift 0xffff bitand ORIS ]
+        [ 0xffff bitand ORI ]
+    } 3cleave ;
+
+: jit-trap-null ( src -- ) drop ;
+: jit-load-vm ( dst -- )
+    0 LOAD64 0 rc-absolute-ppc-2/2/2/2 jit-vm ;
+: jit-load-dlsym ( dst string -- )
+    [ 0 LOAD64 ] dip rc-absolute-ppc-2/2/2/2 jit-dlsym ;
+: jit-load-dlsym-toc ( string -- )
+    [ 2 0 LOAD64 ] dip rc-absolute-ppc-2/2/2/2 jit-dlsym-toc ;
+: jit-load-vm-arg ( dst -- )
+    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-vm jit-rel ;
+: jit-load-entry-point-arg ( dst -- )
+    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-entry-point jit-rel ;
+: jit-load-this-arg ( dst -- )
+    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-this jit-rel ;
+: jit-load-literal-arg ( dst -- )
+    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-literal jit-rel ;
+: jit-load-dlsym-arg ( dst -- )
+    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-dlsym jit-rel ;
+: jit-load-dlsym-toc-arg ( -- )
+    2 0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-dlsym-toc jit-rel ;
+: jit-load-here-arg ( dst -- )
+    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-here jit-rel ;
+: jit-load-megamorphic-cache-arg ( dst -- )
+    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-megamorphic-cache-hits jit-rel ;
+: jit-load-cell ( dst src offset -- ) LD ;
+: jit-load-cell-x ( dst src offset -- ) LDX ;
+: jit-load-cell-update ( dst src offset -- ) LDU ;
+: jit-save-cell ( dst src offset -- ) STD ;
+: jit-save-cell-x ( dst src offset -- ) STDX ;
+: jit-save-cell-update ( dst src offset -- ) STDU ;
+: jit-load-int ( dst src offset -- ) LD ;
+: jit-save-int ( dst src offset -- ) STD ;
+: jit-shift-tag-bits ( dst src -- ) tag-bits get SRADI ;
+: jit-mask-tag-bits ( dst src -- ) tag-bits get CLRRDI ;
+: jit-shift-fixnum-slot ( dst src -- ) 1 SRADI ;
+: jit-class-hashcode ( dst src -- ) 1 SRADI ;
+: jit-shift-left-logical ( dst src n -- ) SLD ;
+: jit-shift-left-logical-imm ( dst src n -- ) SLDI ;
+: jit-shift-right-algebraic ( dst src n -- ) SRAD ;
+: jit-divide ( dst ra rb -- ) DIVD ;
+: jit-multiply-low ( dst ra rb -- ) MULLD ;
+: jit-multiply-low-ov-rc ( dst ra rb -- ) MULLDO. ;
+: jit-compare-cell ( cr ra rb -- ) CMPD ;
+: jit-compare-cell-imm ( cr ra imm -- ) CMPDI ;
+
+: cell-size ( -- n ) 8 ;
+: factor-area-size ( -- n ) 32 ;
+: param-size ( -- n ) 64 ;
+: saved-int-regs-size ( -- n ) 192 ;
+
+<< "vocab:bootstrap/assembler/ppc.factor" parse-file suffix! >>
+call
diff --git a/basis/bootstrap/assembler/ppc.factor b/basis/bootstrap/assembler/ppc.factor
new file mode 100644 (file)
index 0000000..c0f565e
--- /dev/null
@@ -0,0 +1,845 @@
+! Copyright (C) 2011 Erik Charlebois
+! See http://factorcode.org/license.txt for BSD license.
+USING: bootstrap.image.private kernel kernel.private namespaces
+system cpu.ppc.assembler compiler.units compiler.constants math
+math.private math.ranges layouts words vocabs slots.private
+locals locals.backend generic.single.private fry sequences
+threads.private strings.private ;
+FROM: cpu.ppc.assembler => B ;
+IN: bootstrap.ppc
+
+: jit-call ( string -- )
+    dup
+    0 swap jit-load-dlsym
+    0 MTLR
+    jit-load-dlsym-toc
+    BLRL ;
+
+: jit-call-quot ( -- )
+    4 quot-entry-point-offset LI
+    4 3 4 jit-load-cell-x
+    4 MTLR
+    BLRL ;
+
+: jit-jump-quot ( -- )
+    4 quot-entry-point-offset LI
+    4 3 4 jit-load-cell-x
+    4 MTCTR
+    BCTR ;
+
+: stack-frame ( -- n )
+    reserved-size factor-area-size + 16 align ;
+
+: save-at ( m -- n ) reserved-size + param-size + ;
+
+: save-int ( reg off -- ) [ 1 ] dip save-at jit-save-int ;
+: save-fp  ( reg off -- ) [ 1 ] dip save-at STFD ;
+: save-vec ( reg offt -- ) save-at 11 swap LI 11 1 STVXL ;
+: restore-int ( reg off -- ) [ 1 ] dip save-at jit-load-int ;
+: restore-fp  ( reg off -- ) [ 1 ] dip save-at LFD ;
+: restore-vec ( reg offt -- ) save-at 11 swap LI 11 1 LVXL ;
+
+! Stop using intervals here.
+: nv-fp-regs  ( -- seq ) 14 31 [a,b] ;
+: nv-vec-regs ( -- seq ) 20 31 [a,b] ;
+
+: saved-fp-regs-size  ( -- n ) 144 ;
+: saved-vec-regs-size ( -- n ) 192 ;
+
+: callback-frame-size ( -- n )
+    reserved-size
+    param-size +
+    saved-int-regs-size +
+    saved-fp-regs-size +
+    saved-vec-regs-size +
+    16 align ;
+
+: old-context-save-offset ( -- n )
+    cell-size 20 * saved-fp-regs-size + saved-vec-regs-size + save-at ;
+
+[
+    ! Save old stack pointer
+    11 1 MR
+
+    0 MFLR                                           ! Get return address
+    0 1 lr-save jit-save-cell                        ! Stash return address
+    1 1 callback-frame-size neg jit-save-cell-update ! Bump stack pointer and set back chain
+
+    ! Save all non-volatile registers
+    nv-int-regs [ cell-size * save-int ] each-index
+    nv-fp-regs [ 8 * saved-int-regs-size + save-fp  ] each-index
+    ! nv-vec-regs [ 16 * saved-int-regs-size saved-fp-regs-size + + save-vec ] each-index
+
+    ! Stick old stack pointer in the frame register so callbacks
+    ! can access their arguments
+    frame-reg 11 MR
+
+    ! Load VM into vm-reg
+    vm-reg jit-load-vm-arg
+
+    ! Save old context
+    0 vm-reg vm-context-offset jit-load-cell
+    0 1 old-context-save-offset jit-save-cell
+
+    ! Switch over to the spare context
+    11 vm-reg vm-spare-context-offset jit-load-cell
+    11 vm-reg vm-context-offset jit-save-cell
+
+    ! Save C callstack pointer and load Factor callstack
+    1 11 context-callstack-save-offset jit-save-cell
+    1 11 context-callstack-bottom-offset jit-load-cell
+
+    ! Load new data and retain stacks
+    rs-reg 11 context-retainstack-offset jit-load-cell
+    ds-reg 11 context-datastack-offset jit-load-cell
+
+    ! Call into Factor code
+    0 jit-load-entry-point-arg
+    0 MTLR
+    BLRL
+
+    ! Load VM again, pointlessly
+    vm-reg jit-load-vm-arg
+
+    ! Load C callstack pointer
+    11 vm-reg vm-context-offset jit-load-cell
+    1 11 context-callstack-save-offset jit-load-cell
+
+    ! Load old context
+    0 1 old-context-save-offset jit-load-cell
+    0 vm-reg vm-context-offset jit-save-cell
+
+    ! Restore non-volatile registers
+    ! nv-vec-regs [ 16 * saved-int-regs-size saved-float-regs-size + + restore-vec ] each-index
+    nv-fp-regs [ 8 * saved-int-regs-size + restore-fp ] each-index
+    nv-int-regs [ cell-size * restore-int ] each-index
+
+    1 1 callback-frame-size ADDI ! Bump stack back up
+    0 1 lr-save jit-load-cell    ! Fetch return address
+    0 MTLR                       ! Set up return
+    BLR                          ! Branch back
+] callback-stub jit-define
+
+: jit-conditional* ( test-quot false-quot -- )
+    [ '[ 4 + @ ] ] dip jit-conditional ; inline
+
+: jit-load-context ( -- )
+    ctx-reg vm-reg vm-context-offset jit-load-cell ;
+
+: jit-save-context ( -- )
+    jit-load-context
+    1 ctx-reg context-callstack-top-offset jit-save-cell
+    ds-reg ctx-reg context-datastack-offset jit-save-cell
+    rs-reg ctx-reg context-retainstack-offset jit-save-cell ;
+
+: jit-restore-context ( -- )
+    ds-reg ctx-reg context-datastack-offset jit-load-cell
+    rs-reg ctx-reg context-retainstack-offset jit-load-cell ;
+
+[
+    12 jit-load-literal-arg
+    0 profile-count-offset LI
+    11 12 0 jit-load-cell-x
+    11 11 1 tag-fixnum ADDI
+    11 12 0 jit-save-cell-x
+    0 word-code-offset LI
+    11 12 0 jit-load-cell-x
+    11 11 compiled-header-size ADDI
+    11 MTCTR
+    BCTR
+] jit-profiling jit-define
+
+[
+    0 MFLR
+    0 1 lr-save jit-save-cell
+    0 jit-load-this-arg
+    0 1 cell-size 2 * neg jit-save-cell
+    0 stack-frame LI
+    0 1 cell-size 1 * neg jit-save-cell
+    1 1 stack-frame neg jit-save-cell-update
+] jit-prolog jit-define
+
+[
+    3 jit-load-literal-arg
+    3 ds-reg cell-size jit-save-cell-update
+] jit-push jit-define
+
+[
+    jit-save-context
+    3 vm-reg MR
+    4 jit-load-dlsym-arg
+    4 MTLR
+    jit-load-dlsym-toc-arg ! Restore the TOC/GOT
+    BLRL
+    jit-restore-context
+] jit-primitive jit-define
+
+[ 0 BL rc-relative-ppc-3-pc rt-entry-point-pic jit-rel ] jit-word-call jit-define
+
+[
+    6 jit-load-here-arg
+    0 B rc-relative-ppc-3-pc rt-entry-point-pic-tail jit-rel
+] jit-word-jump jit-define
+
+[
+    3 ds-reg 0 jit-load-cell
+    ds-reg dup cell-size SUBI
+    0 3 \ f type-number jit-compare-cell-imm
+    [ 0 swap BEQ ] [ 0 B rc-relative-ppc-3-pc rt-entry-point jit-rel ] jit-conditional*
+    0 B rc-relative-ppc-3-pc rt-entry-point jit-rel
+] jit-if jit-define
+
+: jit->r ( -- )
+    4 ds-reg 0 jit-load-cell
+    ds-reg dup cell-size SUBI
+    4 rs-reg cell-size jit-save-cell-update ;
+
+: jit-2>r ( -- )
+    4 ds-reg 0 jit-load-cell
+    5 ds-reg cell-size neg jit-load-cell
+    ds-reg dup 2 cell-size * SUBI
+    rs-reg dup 2 cell-size * ADDI
+    4 rs-reg 0 jit-save-cell
+    5 rs-reg cell-size neg jit-save-cell ;
+
+: jit-3>r ( -- )
+    4 ds-reg 0 jit-load-cell
+    5 ds-reg cell-size neg jit-load-cell
+    6 ds-reg cell-size neg 2 * jit-load-cell
+    ds-reg dup 3 cell-size * SUBI
+    rs-reg dup 3 cell-size * ADDI
+    4 rs-reg 0 jit-save-cell
+    5 rs-reg cell-size neg jit-save-cell
+    6 rs-reg cell-size neg 2 * jit-save-cell ;
+
+: jit-r> ( -- )
+    4 rs-reg 0 jit-load-cell
+    rs-reg dup cell-size SUBI
+    4 ds-reg cell-size jit-save-cell-update ;
+
+: jit-2r> ( -- )
+    4 rs-reg 0 jit-load-cell
+    5 rs-reg cell-size neg jit-load-cell
+    rs-reg dup 2 cell-size * SUBI
+    ds-reg dup 2 cell-size * ADDI
+    4 ds-reg 0 jit-save-cell
+    5 ds-reg cell-size neg jit-save-cell ;
+
+: jit-3r> ( -- )
+    4 rs-reg 0 jit-load-cell
+    5 rs-reg cell-size neg jit-load-cell
+    6 rs-reg cell-size neg 2 * jit-load-cell
+    rs-reg dup 3 cell-size * SUBI
+    ds-reg dup 3 cell-size * ADDI
+    4 ds-reg 0 jit-save-cell
+    5 ds-reg cell-size neg jit-save-cell
+    6 ds-reg cell-size neg 2 * jit-save-cell ;
+
+[
+    jit->r
+    0 BL rc-relative-ppc-3-pc rt-entry-point jit-rel
+    jit-r>
+] jit-dip jit-define
+
+[
+    jit-2>r
+    0 BL rc-relative-ppc-3-pc rt-entry-point jit-rel
+    jit-2r>
+] jit-2dip jit-define
+
+[
+    jit-3>r
+    0 BL rc-relative-ppc-3-pc rt-entry-point jit-rel
+    jit-3r>
+] jit-3dip jit-define
+
+[
+    1 1 stack-frame ADDI
+    0 1 lr-save jit-load-cell
+    0 MTLR
+] jit-epilog jit-define
+
+[ BLR ] jit-return jit-define
+
+! ! ! Polymorphic inline caches
+
+! Don't touch r6 here; it's used to pass the tail call site
+! address for tail PICs
+
+! Load a value from a stack position
+[
+    4 ds-reg 0 jit-load-cell rc-absolute-ppc-2 rt-untagged jit-rel
+] pic-load jit-define
+
+[ 4 4 tag-mask get ANDI. ] pic-tag jit-define
+
+[
+    3 4 MR
+    4 4 tag-mask get ANDI.
+    0 4 tuple type-number jit-compare-cell-imm
+    [ 0 swap BNE ]
+    [ 4 tuple-class-offset LI 4 3 4 jit-load-cell-x ]
+    jit-conditional*
+] pic-tuple jit-define
+
+[
+    0 4 0 jit-compare-cell-imm rc-absolute-ppc-2 rt-untagged jit-rel
+] pic-check-tag jit-define
+
+[
+    5 jit-load-literal-arg
+    0 4 5 jit-compare-cell
+] pic-check-tuple jit-define
+
+[
+    [ 0 swap BNE ] [ 0 B rc-relative-ppc-3-pc rt-entry-point jit-rel ] jit-conditional*
+] pic-hit jit-define
+
+! Inline cache miss entry points
+: jit-load-return-address ( -- ) 6 MFLR ;
+
+! These are always in tail position with an existing stack
+! frame, and the stack. The frame setup takes this into account.
+: jit-inline-cache-miss ( -- )
+    jit-save-context
+    3 6 MR
+    4 vm-reg MR
+    ctx-reg 6 MR
+    "inline_cache_miss" jit-call
+    6 ctx-reg MR
+    jit-load-context
+    jit-restore-context ;
+
+[ jit-load-return-address jit-inline-cache-miss ]
+[ 3 MTLR BLRL ]
+[ 3 MTCTR BCTR ]
+\ inline-cache-miss define-combinator-primitive
+
+[ jit-inline-cache-miss ]
+[ 3 MTLR BLRL ]
+[ 3 MTCTR BCTR ]
+\ inline-cache-miss-tail define-combinator-primitive
+
+! ! ! Megamorphic caches
+
+[
+    ! class = ...
+    3 4 MR
+    4 4 tag-mask get ANDI. ! Mask and...
+    4 4 tag-bits get jit-shift-left-logical-imm ! shift tag bits to fixnum
+    0 4 tuple type-number tag-fixnum jit-compare-cell-imm
+    [ 0 swap BNE ]
+    [ 4 tuple-class-offset LI 4 3 4 jit-load-cell-x ]
+    jit-conditional*
+    ! cache = ...
+    3 jit-load-literal-arg
+    ! key = hashcode(class)
+    5 4 jit-class-hashcode
+    ! key &= cache.length - 1
+    5 5 mega-cache-size get 1 - 4 * ANDI.
+    ! cache += array-start-offset
+    3 3 array-start-offset ADDI
+    ! cache += key
+    3 3 5 ADD
+    ! if(get(cache) == class)
+    6 3 0 jit-load-cell
+    0 6 4 jit-compare-cell
+    [ 0 swap BNE ]
+    [
+        ! megamorphic_cache_hits++
+        4 jit-load-megamorphic-cache-arg
+        5 4 0 jit-load-cell
+        5 5 1 ADDI
+        5 4 0 jit-save-cell
+        ! ... goto get(cache + cell-size)
+        5 word-entry-point-offset LI
+        3 3 cell-size jit-load-cell
+        3 3 5 jit-load-cell-x
+        3 MTCTR
+        BCTR
+    ]
+    jit-conditional*
+    ! fall-through on miss
+] mega-lookup jit-define
+
+! ! ! Sub-primitives
+
+! Quotations and words
+[
+    3 ds-reg 0 jit-load-cell
+    ds-reg dup cell-size SUBI
+]
+[ jit-call-quot ]
+[ jit-jump-quot ] \ (call) define-combinator-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    ds-reg dup cell-size SUBI
+    4 word-entry-point-offset LI
+    4 3 4 jit-load-cell-x
+]
+[ 4 MTLR BLRL ]
+[ 4 MTCTR BCTR ] \ (execute) define-combinator-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    ds-reg dup cell-size SUBI
+    4 word-entry-point-offset LI
+    4 3 4 jit-load-cell-x
+    4 MTCTR BCTR
+] jit-execute jit-define
+
+! Special primitives
+[
+    frame-reg 3 MR
+
+    3 vm-reg MR
+    "begin_callback" jit-call
+
+    jit-load-context
+    jit-restore-context
+
+    ! Call quotation
+    3 frame-reg MR
+    jit-call-quot
+
+    jit-save-context
+
+    3 vm-reg MR
+    "end_callback" jit-call
+] \ c-to-factor define-sub-primitive
+
+[
+    ! Unwind stack frames
+    1 4 MR
+
+    ! Load VM pointer into vm-reg, since we're entering from
+    ! C code
+    vm-reg jit-load-vm
+
+    ! Load ds and rs registers
+    jit-load-context
+    jit-restore-context
+
+    ! We have changed the stack; load return address again
+    0 1 lr-save jit-load-cell
+    0 MTLR
+
+    ! Call quotation
+    jit-jump-quot
+] \ unwind-native-frames define-sub-primitive
+
+[
+    7 0 LI
+    7 1 lr-save jit-save-cell
+
+    ! Load callstack object
+    6 ds-reg 0 jit-load-cell
+    ds-reg ds-reg cell-size SUBI
+    ! Get ctx->callstack_bottom
+    jit-load-context
+    3 ctx-reg context-callstack-bottom-offset jit-load-cell
+    ! Get top of callstack object -- 'src' for memcpy
+    4 6 callstack-top-offset ADDI
+    ! Get callstack length, in bytes --- 'len' for memcpy
+    7 callstack-length-offset LI
+    5 6 7 jit-load-cell-x
+    5 5 jit-shift-tag-bits
+    ! Compute new stack pointer -- 'dst' for memcpy
+    3 3 5 SUB
+    ! Install new stack pointer
+    1 3 MR
+    ! Call memcpy; arguments are now in the correct registers
+    1 1 -16 cell-size * jit-save-cell-update
+    "factor_memcpy" jit-call
+    1 1 0 jit-load-cell
+    ! Return with new callstack
+    0 1 lr-save jit-load-cell
+    0 MTLR
+    BLR
+] \ set-callstack define-sub-primitive
+
+[
+    jit-save-context
+    4 vm-reg MR
+    "lazy_jit_compile" jit-call
+]
+[ jit-call-quot ]
+[ jit-jump-quot ]
+\ lazy-jit-compile define-combinator-primitive
+
+! Objects
+[
+    3 ds-reg 0 jit-load-cell
+    3 3 tag-mask get ANDI.
+    3 3 tag-bits get jit-shift-left-logical-imm
+    3 ds-reg 0 jit-save-cell
+] \ tag define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell   ! Load m
+    4 ds-reg cell-size neg jit-load-cell-update ! Load obj
+    3 3 jit-shift-fixnum-slot  ! Shift to a cell-size multiple
+    4 4 jit-mask-tag-bits      ! Clear tag bits on obj
+    3 4 3 jit-load-cell-x      ! Load cell at &obj[m]
+    3 ds-reg 0 jit-save-cell   ! Push the result to the stack
+] \ slot define-sub-primitive
+
+[
+    ! load string index from stack
+    3 ds-reg cell-size neg jit-load-cell
+    3 3 jit-shift-tag-bits
+    ! load string from stack
+    4 ds-reg 0 jit-load-cell
+    ! load character
+    4 4 string-offset ADDI
+    3 3 4 LBZX
+    3 3 tag-bits get jit-shift-left-logical-imm
+    ! store character to stack
+    ds-reg ds-reg cell-size SUBI
+    3 ds-reg 0 jit-save-cell
+] \ string-nth-fast define-sub-primitive
+
+! Shufflers
+[
+    ds-reg dup cell-size SUBI
+] \ drop define-sub-primitive
+
+[
+    ds-reg dup 2 cell-size * SUBI
+] \ 2drop define-sub-primitive
+
+[
+    ds-reg dup 3 cell-size * SUBI
+] \ 3drop define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    3 ds-reg cell-size jit-save-cell-update
+] \ dup define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    4 ds-reg cell-size neg jit-load-cell
+    ds-reg dup 2 cell-size * ADDI
+    3 ds-reg 0 jit-save-cell
+    4 ds-reg cell-size neg jit-save-cell
+] \ 2dup define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    4 ds-reg cell-size neg jit-load-cell
+    5 ds-reg cell-size neg 2 * jit-load-cell
+    ds-reg dup cell-size 3 * ADDI
+    3 ds-reg 0 jit-save-cell
+    4 ds-reg cell-size neg jit-save-cell
+    5 ds-reg cell-size neg 2 * jit-save-cell
+] \ 3dup define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    ds-reg dup cell-size SUBI
+    3 ds-reg 0 jit-save-cell
+] \ nip define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    ds-reg dup cell-size 2 * SUBI
+    3 ds-reg 0 jit-save-cell
+] \ 2nip define-sub-primitive
+
+[
+    3 ds-reg cell-size neg jit-load-cell
+    3 ds-reg cell-size jit-save-cell-update
+] \ over define-sub-primitive
+
+[
+    3 ds-reg cell-size neg 2 * jit-load-cell
+    3 ds-reg cell-size jit-save-cell-update
+] \ pick define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    4 ds-reg cell-size neg jit-load-cell
+    4 ds-reg 0 jit-save-cell
+    3 ds-reg cell-size jit-save-cell-update
+] \ dupd define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    4 ds-reg cell-size neg jit-load-cell
+    3 ds-reg cell-size neg jit-save-cell
+    4 ds-reg 0 jit-save-cell
+] \ swap define-sub-primitive
+
+[
+    3 ds-reg cell-size neg jit-load-cell
+    4 ds-reg cell-size neg 2 * jit-load-cell
+    3 ds-reg cell-size neg 2 * jit-save-cell
+    4 ds-reg cell-size neg jit-save-cell
+] \ swapd define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    4 ds-reg cell-size neg jit-load-cell
+    5 ds-reg cell-size neg 2 * jit-load-cell
+    4 ds-reg cell-size neg 2 * jit-save-cell
+    3 ds-reg cell-size neg jit-save-cell
+    5 ds-reg 0 jit-save-cell
+] \ rot define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    4 ds-reg cell-size neg jit-load-cell
+    5 ds-reg cell-size neg 2 * jit-load-cell
+    3 ds-reg cell-size neg 2 * jit-save-cell
+    5 ds-reg cell-size neg jit-save-cell
+    4 ds-reg 0 jit-save-cell
+] \ -rot define-sub-primitive
+
+[ jit->r ] \ load-local define-sub-primitive
+
+! Comparisons
+: jit-compare ( insn -- )
+    t jit-literal
+    3 jit-load-literal-arg
+    4 ds-reg 0 jit-load-cell
+    5 ds-reg cell-size neg jit-load-cell-update
+    0 5 4 jit-compare-cell
+    [ 0 8 ] dip execute( cr offset -- )
+    3 \ f type-number LI
+    3 ds-reg 0 jit-save-cell ;
+
+: define-jit-compare ( insn word -- )
+    [ [ jit-compare ] curry ] dip define-sub-primitive ;
+
+\ BEQ \ eq? define-jit-compare
+\ BGE \ fixnum>= define-jit-compare
+\ BLE \ fixnum<= define-jit-compare
+\ BGT \ fixnum> define-jit-compare
+\ BLT \ fixnum< define-jit-compare
+
+! Math
+[
+    3 ds-reg 0 jit-load-cell
+    ds-reg ds-reg cell-size SUBI
+    4 ds-reg 0 jit-load-cell
+    3 3 4 OR
+    3 3 tag-mask get ANDI.
+    4 \ f type-number LI
+    0 3 0 jit-compare-cell-imm
+    [ 0 swap BNE ] [ 4 1 tag-fixnum LI ] jit-conditional*
+    4 ds-reg 0 jit-save-cell
+] \ both-fixnums? define-sub-primitive
+
+: jit-math ( insn -- )
+    3 ds-reg 0 jit-load-cell
+    4 ds-reg cell-size neg jit-load-cell-update
+    [ 5 3 4 ] dip execute( dst src1 src2 -- )
+    5 ds-reg 0 jit-save-cell ;
+
+[ \ ADD jit-math ] \ fixnum+fast define-sub-primitive
+
+[ \ SUBF jit-math ] \ fixnum-fast define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    4 ds-reg cell-size neg jit-load-cell-update
+    4 4 jit-shift-tag-bits
+    5 3 4 jit-multiply-low
+    5 ds-reg 0 jit-save-cell
+] \ fixnum*fast define-sub-primitive
+
+[ \ AND jit-math ] \ fixnum-bitand define-sub-primitive
+
+[ \ OR jit-math ] \ fixnum-bitor define-sub-primitive
+
+[ \ XOR jit-math ] \ fixnum-bitxor define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    3 3 NOT
+    3 3 tag-mask get XORI
+    3 ds-reg 0 jit-save-cell
+] \ fixnum-bitnot define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell ! Load amount to shift
+    3 3 jit-shift-tag-bits   ! Shift out tag bits
+    ds-reg ds-reg cell-size SUBI
+    4 ds-reg 0 jit-load-cell ! Load value to shift
+    5 4 3 jit-shift-left-logical    ! Shift left
+    6 3 NEG                         ! Negate shift amount
+    7 4 6 jit-shift-right-algebraic ! Shift right
+    7 7 jit-mask-tag-bits           ! Mask out tag bits
+    0 3 0 jit-compare-cell-imm
+    [ 0 swap BGT ] [ 5 7 MR ] jit-conditional*
+    5 ds-reg 0 jit-save-cell
+] \ fixnum-shift-fast define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    ds-reg ds-reg cell-size SUBI
+    4 ds-reg 0 jit-load-cell
+    5 4 3 jit-divide
+    6 5 3 jit-multiply-low
+    7 4 6 SUB
+    7 ds-reg 0 jit-save-cell
+] \ fixnum-mod define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    ds-reg ds-reg cell-size SUBI
+    4 ds-reg 0 jit-load-cell
+    5 4 3 jit-divide
+    5 5 tag-bits get jit-shift-left-logical-imm
+    5 ds-reg 0 jit-save-cell
+] \ fixnum/i-fast define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    4 ds-reg cell-size neg jit-load-cell
+    5 4 3 jit-divide
+    6 5 3 jit-multiply-low
+    7 4 6 SUB
+    5 5 tag-bits get jit-shift-left-logical-imm
+    5 ds-reg cell-size neg jit-save-cell
+    7 ds-reg 0 jit-save-cell
+] \ fixnum/mod-fast define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    3 3 jit-shift-fixnum-slot
+    3 rs-reg 3 jit-load-cell-x
+    3 ds-reg 0 jit-save-cell
+] \ get-local define-sub-primitive
+
+[
+    3 ds-reg 0 jit-load-cell
+    ds-reg ds-reg cell-size SUBI
+    3 3 jit-shift-fixnum-slot
+    rs-reg rs-reg 3 SUB
+] \ drop-locals define-sub-primitive
+
+! Overflowing fixnum arithmetic
+:: jit-overflow ( insn func -- )
+    ds-reg ds-reg cell-size SUBI
+    jit-save-context
+    3 ds-reg 0 jit-load-cell
+    4 ds-reg cell-size jit-load-cell
+    0 0 LI
+    0 MTXER
+    6 4 3 insn call( d a s -- )
+    6 ds-reg 0 jit-save-cell
+    [ 0 swap BNS ]
+    [
+        5 vm-reg MR
+        func jit-call
+    ]
+    jit-conditional* ;
+
+[ [ ADDO. ] "overflow_fixnum_add" jit-overflow ] \ fixnum+ define-sub-primitive
+
+[ [ SUBFO. ] "overflow_fixnum_subtract" jit-overflow ] \ fixnum- define-sub-primitive
+
+[
+    ds-reg ds-reg cell-size SUBI
+    jit-save-context
+    3 ds-reg 0 jit-load-cell
+    3 3 jit-shift-tag-bits
+    4 ds-reg cell-size jit-load-cell
+    0 0 LI
+    0 MTXER
+    6 3 4 jit-multiply-low-ov-rc
+    6 ds-reg 0 jit-save-cell
+    [ 0 swap BNS ]
+    [
+        4 4 jit-shift-tag-bits
+        5 vm-reg MR
+        "overflow_fixnum_multiply" jit-call
+    ]
+    jit-conditional*
+] \ fixnum* define-sub-primitive
+
+! Contexts
+:: jit-switch-context ( reg -- )
+    7 0 LI
+    7 1 lr-save jit-save-cell
+
+    ! Make the new context the current one
+    ctx-reg reg MR
+    ctx-reg vm-reg vm-context-offset jit-save-cell
+
+    ! Load new stack pointer
+    1 ctx-reg context-callstack-top-offset jit-load-cell
+
+    ! Load new ds, rs registers
+    jit-restore-context ;
+
+: jit-pop-context-and-param ( -- )
+    3 ds-reg 0 jit-load-cell
+    4 alien-offset LI
+    3 3 4 jit-load-cell-x
+    4 ds-reg cell-size neg jit-load-cell
+    ds-reg ds-reg cell-size 2 * SUBI ;
+
+: jit-push-param ( -- )
+    ds-reg ds-reg cell-size ADDI
+    4 ds-reg 0 jit-save-cell ;
+
+: jit-set-context ( -- )
+    jit-pop-context-and-param
+    jit-save-context
+    3 jit-switch-context
+    jit-push-param ;
+
+[ jit-set-context ] \ (set-context) define-sub-primitive
+
+: jit-pop-quot-and-param ( -- )
+    3 ds-reg 0 jit-load-cell
+    4 ds-reg cell-size neg jit-load-cell
+    ds-reg ds-reg cell-size 2 * SUBI ;
+
+: jit-start-context ( -- )
+    ! Create the new context in return-reg. Have to save context
+    ! twice, first before calling new_context() which may GC,
+    ! and again after popping the two parameters from the stack.
+    jit-save-context
+    3 vm-reg MR
+    "new_context" jit-call
+
+    6 3 MR
+    jit-pop-quot-and-param
+    jit-save-context
+    6 jit-switch-context
+    jit-push-param
+    jit-jump-quot ;
+
+[ jit-start-context ] \ (start-context) define-sub-primitive
+
+: jit-delete-current-context ( -- )
+    jit-load-context
+    3 vm-reg MR
+    4 ctx-reg MR
+    "delete_context" jit-call ;
+
+[
+    jit-delete-current-context
+    jit-set-context
+] \ (set-context-and-delete) define-sub-primitive
+
+: jit-start-context-and-delete ( -- )
+    jit-load-context
+    3 vm-reg MR
+    4 ctx-reg MR
+    "reset_context" jit-call
+    jit-pop-quot-and-param
+    ctx-reg jit-switch-context
+    jit-push-param
+    jit-jump-quot ;
+
+[
+    jit-start-context-and-delete
+] \ (start-context-and-delete) define-sub-primitive
+
+[ "bootstrap.ppc" forget-vocab ] with-compilation-unit
diff --git a/basis/bootstrap/assembler/x86.32.factor b/basis/bootstrap/assembler/x86.32.factor
new file mode 100644 (file)
index 0000000..b601c86
--- /dev/null
@@ -0,0 +1,371 @@
+! Copyright (C) 2007, 2011 Slava Pestov.
+! See http://factorcode.org/license.txt for BSD license.
+USING: bootstrap.image.private kernel kernel.private namespaces
+system cpu.x86.assembler cpu.x86.assembler.operands layouts
+vocabs parser compiler.constants compiler.codegen.relocation
+sequences math math.private generic.single.private
+threads.private locals ;
+IN: bootstrap.x86
+
+4 \ cell set
+
+: leaf-stack-frame-size ( -- n ) 4 bootstrap-cells ;
+: signal-handler-stack-frame-size ( -- n ) 12 bootstrap-cells ;
+: stack-frame-size ( -- n ) 8 bootstrap-cells ;
+: shift-arg ( -- reg ) ECX ;
+: div-arg ( -- reg ) EAX ;
+: mod-arg ( -- reg ) EDX ;
+: temp0 ( -- reg ) EAX ;
+: temp1 ( -- reg ) ECX ;
+: temp2 ( -- reg ) EBX ;
+: temp3 ( -- reg ) EDX ;
+: pic-tail-reg ( -- reg ) EDX ;
+: stack-reg ( -- reg ) ESP ;
+: frame-reg ( -- reg ) EBP ;
+: vm-reg ( -- reg ) EBX ;
+: ctx-reg ( -- reg ) EBP ;
+: nv-regs ( -- seq ) { ESI EDI EBX } ;
+: volatile-regs ( -- seq ) { EAX ECX EDX } ;
+: nv-reg ( -- reg ) ESI ;
+: ds-reg ( -- reg ) ESI ;
+: rs-reg ( -- reg ) EDI ;
+: link-reg ( -- reg ) EBX ;
+: fixnum>slot@ ( -- ) temp0 2 SAR ;
+: rex-length ( -- n ) 0 ;
+: red-zone-size ( -- n ) 0 ;
+
+: jit-call ( name -- )
+    0 CALL f rc-relative rel-dlsym ;
+
+[
+    pic-tail-reg 0 MOV 0 rc-absolute-cell rel-here
+    0 JMP f rc-relative rel-word-pic-tail
+] jit-word-jump jit-define
+
+: jit-load-vm ( -- )
+    vm-reg 0 MOV 0 rc-absolute-cell rel-vm ;
+
+: jit-load-context ( -- )
+    ! VM pointer must be in vm-reg already
+    ctx-reg vm-reg vm-context-offset [+] MOV ;
+
+: jit-save-context ( -- )
+    jit-load-context
+    ECX ESP -4 [+] LEA
+    ctx-reg context-callstack-top-offset [+] ECX MOV
+    ctx-reg context-datastack-offset [+] ds-reg MOV
+    ctx-reg context-retainstack-offset [+] rs-reg MOV ;
+
+: jit-restore-context ( -- )
+    ds-reg ctx-reg context-datastack-offset [+] MOV
+    rs-reg ctx-reg context-retainstack-offset [+] MOV ;
+
+[
+    ! ctx-reg is preserved across the call because it is
+    ! non-volatile in the C ABI
+    jit-load-vm
+    jit-save-context
+    ! call the primitive
+    ESP [] vm-reg MOV
+    0 CALL f f rc-relative rel-dlsym
+    jit-restore-context
+] jit-primitive jit-define
+
+: jit-jump-quot ( -- )
+    EAX quot-entry-point-offset [+] JMP ;
+
+: jit-call-quot ( -- )
+    EAX quot-entry-point-offset [+] CALL ;
+
+[
+    jit-load-vm
+    ESP [] vm-reg MOV
+    EAX EBP 8 [+] MOV
+    ESP 4 [+] EAX MOV
+    "begin_callback" jit-call
+
+    jit-call-quot
+
+    jit-load-vm
+    ESP [] vm-reg MOV
+    "end_callback" jit-call
+] \ c-to-factor define-sub-primitive
+
+: signal-handler-save-regs ( -- regs )
+    { EAX ECX EDX EBX EBP ESI EDI } ;
+
+[
+    EAX ds-reg [] MOV
+    ds-reg bootstrap-cell SUB
+]
+[ jit-call-quot ]
+[ jit-jump-quot ]
+\ (call) define-combinator-primitive
+
+! unwind-native-frames is marked as "special" in vm/quotations.cpp
+! so it does not have a standard prolog
+[
+    ! Load ds and rs registers
+    jit-load-vm
+    jit-load-context
+    jit-restore-context
+
+    ! clear the fault flag
+    vm-reg vm-fault-flag-offset [+] 0 MOV
+
+    ! Windows-specific setup
+    ctx-reg jit-update-seh
+
+    ! Load arguments
+    EAX ESP bootstrap-cell [+] MOV
+    EDX ESP 2 bootstrap-cells [+] MOV
+
+    ! Unwind stack frames
+    ESP EDX MOV
+
+    jit-jump-quot
+] \ unwind-native-frames define-sub-primitive
+
+[
+    ESP 2 SUB
+    ESP [] FNSTCW
+    FNINIT
+    AX ESP [] MOV
+    ESP 2 ADD
+] \ fpu-state define-sub-primitive
+
+[
+    ESP stack-frame-size [+] FLDCW
+] \ set-fpu-state define-sub-primitive
+
+[
+    ! Load callstack object
+    temp3 ds-reg [] MOV
+    ds-reg bootstrap-cell SUB
+    ! Get ctx->callstack_bottom
+    jit-load-vm
+    jit-load-context
+    temp0 ctx-reg context-callstack-bottom-offset [+] MOV
+    ! Get top of callstack object -- 'src' for memcpy
+    temp1 temp3 callstack-top-offset [+] LEA
+    ! Get callstack length, in bytes --- 'len' for memcpy
+    temp2 temp3 callstack-length-offset [+] MOV
+    temp2 tag-bits get SHR
+    ! Compute new stack pointer -- 'dst' for memcpy
+    temp0 temp2 SUB
+    ! Install new stack pointer
+    ESP temp0 MOV
+    ! Call memcpy
+    temp2 PUSH
+    temp1 PUSH
+    temp0 PUSH
+    "factor_memcpy" jit-call
+    ESP 12 ADD
+    ! Return with new callstack
+    0 RET
+] \ set-callstack define-sub-primitive
+
+[
+    jit-load-vm
+    jit-save-context
+
+    ! Store arguments
+    ESP [] EAX MOV
+    ESP 4 [+] vm-reg MOV
+
+    ! Call VM
+    "lazy_jit_compile" jit-call
+]
+[ jit-call-quot ]
+[ jit-jump-quot ]
+\ lazy-jit-compile define-combinator-primitive
+
+[
+    temp1 0xffffffff CMP f rc-absolute-cell rel-literal
+] pic-check-tuple jit-define
+
+! Inline cache miss entry points
+: jit-load-return-address ( -- )
+    pic-tail-reg ESP stack-frame-size bootstrap-cell - [+] MOV ;
+
+! These are always in tail position with an existing stack
+! frame, and the stack. The frame setup takes this into account.
+: jit-inline-cache-miss ( -- )
+    jit-load-vm
+    jit-save-context
+    ESP 4 [+] vm-reg MOV
+    ESP [] pic-tail-reg MOV
+    0 CALL rc-relative rel-inline-cache-miss
+    jit-restore-context ;
+
+[ jit-load-return-address jit-inline-cache-miss ]
+[ EAX CALL ]
+[ EAX JMP ]
+\ inline-cache-miss define-combinator-primitive
+
+[ jit-inline-cache-miss ]
+[ EAX CALL ]
+[ EAX JMP ]
+\ inline-cache-miss-tail define-combinator-primitive
+
+! Overflowing fixnum arithmetic
+: jit-overflow ( insn func -- )
+    ds-reg 4 SUB
+    jit-load-vm
+    jit-save-context
+    EAX ds-reg [] MOV
+    EDX ds-reg 4 [+] MOV
+    EBX EAX MOV
+    [ [ EBX EDX ] dip call( dst src -- ) ] dip
+    ds-reg [] EBX MOV
+    [ JNO ]
+    [
+        ESP [] EAX MOV
+        ESP 4 [+] EDX MOV
+        jit-load-vm
+        ESP 8 [+] vm-reg MOV
+        jit-call
+    ]
+    jit-conditional ;
+
+[ [ ADD ] "overflow_fixnum_add" jit-overflow ] \ fixnum+ define-sub-primitive
+
+[ [ SUB ] "overflow_fixnum_subtract" jit-overflow ] \ fixnum- define-sub-primitive
+
+[
+    ds-reg 4 SUB
+    jit-load-vm
+    jit-save-context
+    EBX ds-reg [] MOV
+    EAX EBX MOV
+    EBP ds-reg 4 [+] MOV
+    EBP tag-bits get SAR
+    EBP IMUL
+    ds-reg [] EAX MOV
+    [ JNO ]
+    [
+        EBX tag-bits get SAR
+        ESP [] EBX MOV
+        ESP 4 [+] EBP MOV
+        jit-load-vm
+        ESP 8 [+] vm-reg MOV
+        "overflow_fixnum_multiply" jit-call
+    ]
+    jit-conditional
+] \ fixnum* define-sub-primitive
+
+! Contexts
+: jit-switch-context ( reg -- )
+    ! Push a bogus return address so the GC can track this frame back
+    ! to the owner
+    0 CALL
+
+    ! Make the new context the current one
+    ctx-reg swap MOV
+    vm-reg vm-context-offset [+] ctx-reg MOV
+
+    ! Load new stack pointer
+    ESP ctx-reg context-callstack-top-offset [+] MOV
+
+    ! Windows-specific setup
+    ctx-reg jit-update-tib
+
+    ! Load new ds, rs registers
+    jit-restore-context ;
+
+: jit-set-context ( -- )
+    ! Load context and parameter from datastack
+    EAX ds-reg [] MOV
+    EAX EAX alien-offset [+] MOV
+    EDX ds-reg -4 [+] MOV
+    ds-reg 8 SUB
+
+    ! Save ds, rs registers
+    jit-load-vm
+    jit-save-context
+
+    ! Make the new context active
+    EAX jit-switch-context
+
+    ! Windows-specific setup
+    ctx-reg jit-update-seh
+
+    ! Twiddle stack for return
+    ESP 4 ADD
+
+    ! Store parameter to datastack
+    ds-reg 4 ADD
+    ds-reg [] EDX MOV ;
+
+[ jit-set-context ] \ (set-context) define-sub-primitive
+
+: jit-save-quot-and-param ( -- )
+    EDX ds-reg MOV
+    ds-reg 8 SUB ;
+
+: jit-push-param ( -- )
+    EAX EDX -4 [+] MOV
+    ds-reg 4 ADD
+    ds-reg [] EAX MOV ;
+
+: jit-start-context ( -- )
+    ! Create the new context in return-reg
+    jit-load-vm
+    jit-save-context
+    ESP [] vm-reg MOV
+    "new_context" jit-call
+
+    jit-save-quot-and-param
+
+    ! Make the new context active
+    jit-load-vm
+    jit-save-context
+    EAX jit-switch-context
+
+    jit-push-param
+
+    ! Windows-specific setup
+    jit-install-seh
+
+    ! Push a fake return address
+    0 PUSH
+
+    ! Jump to initial quotation
+    EAX EDX [] MOV
+    jit-jump-quot ;
+
+[ jit-start-context ] \ (start-context) define-sub-primitive
+
+: jit-delete-current-context ( -- )
+    jit-load-vm
+    jit-load-context
+    ESP [] vm-reg MOV
+    ESP 4 [+] ctx-reg MOV
+    "delete_context" jit-call ;
+
+[
+    jit-delete-current-context
+    jit-set-context
+] \ (set-context-and-delete) define-sub-primitive
+
+: jit-start-context-and-delete ( -- )
+    jit-load-vm
+    jit-load-context
+    ESP [] vm-reg MOV
+    ESP 4 [+] ctx-reg MOV
+    "reset_context" jit-call
+
+    jit-save-quot-and-param
+    ctx-reg jit-switch-context
+    jit-push-param
+
+    EAX EDX [] MOV
+    jit-jump-quot ;
+
+[
+    0 EAX MOVABS rc-absolute rel-safepoint
+] \ jit-safepoint jit-define
+
+[
+    jit-start-context-and-delete
+] \ (start-context-and-delete) define-sub-primitive
diff --git a/basis/bootstrap/assembler/x86.32.unix.factor b/basis/bootstrap/assembler/x86.32.unix.factor
new file mode 100644 (file)
index 0000000..74ac251
--- /dev/null
@@ -0,0 +1,8 @@
+! Copyright (C) 2010 Slava Pestov.
+! See http://factorcode.org/license.txt for BSD license.
+USING: kernel parser sequences ;
+IN: bootstrap.x86
+
+<< "vocab:bootstrap/assembler/x86.unix.factor" parse-file suffix! >> call
+<< "vocab:bootstrap/assembler/x86.32.factor" parse-file suffix! >> call
+<< "vocab:bootstrap/assembler/x86.factor" parse-file suffix! >> call
diff --git a/basis/bootstrap/assembler/x86.32.windows.factor b/basis/bootstrap/assembler/x86.32.windows.factor
new file mode 100644 (file)
index 0000000..fb3efc8
--- /dev/null
@@ -0,0 +1,37 @@
+! Copyright (C) 2010 Slava Pestov.
+! See http://factorcode.org/license.txt for BSD license.
+USING: bootstrap.image.private compiler.constants
+compiler.codegen.relocation cpu.x86.assembler
+cpu.x86.assembler.operands kernel layouts locals parser
+sequences ;
+IN: bootstrap.x86
+
+: tib-segment ( -- ) FS ;
+: tib-temp ( -- reg ) EAX ;
+
+<< "vocab:bootstrap/assembler/x86.windows.factor" parse-file suffix! >> call
+
+: jit-install-seh ( -- )
+    ! Create a new exception record and store it in the TIB.
+    ! Clobbers tib-temp.
+    ! Align stack
+    ESP 3 bootstrap-cells ADD
+    ! Exception handler address filled in by callback.cpp
+    tib-temp 0 MOV rc-absolute-cell rel-exception-handler
+    tib-temp PUSH
+    ! No next handler
+    0 PUSH
+    ! This is the new exception handler
+    tib-exception-list-offset [] ESP tib-segment MOV ;
+
+:: jit-update-seh ( ctx-reg -- )
+    ! Load exception record structure that jit-install-seh
+    ! created from the bottom of the callstack.
+    ! Clobbers tib-temp.
+    tib-temp ctx-reg context-callstack-bottom-offset [+] MOV
+    tib-temp bootstrap-cell ADD
+    ! Store exception record in TIB.
+    tib-exception-list-offset [] tib-temp tib-segment MOV ;
+
+<< "vocab:bootstrap/assembler/x86.32.factor" parse-file suffix! >> call
+<< "vocab:bootstrap/assembler/x86.factor" parse-file suffix! >> call
diff --git a/basis/bootstrap/assembler/x86.64.factor b/basis/bootstrap/assembler/x86.64.factor
new file mode 100644 (file)
index 0000000..be447eb
--- /dev/null
@@ -0,0 +1,322 @@
+! Copyright (C) 2007, 2011 Slava Pestov.
+! See http://factorcode.org/license.txt for BSD license.
+USING: bootstrap.image.private kernel kernel.private namespaces
+system layouts vocabs parser compiler.constants
+compiler.codegen.relocation math math.private cpu.x86.assembler
+cpu.x86.assembler.operands sequences generic.single.private
+threads.private locals ;
+IN: bootstrap.x86
+
+8 \ cell set
+
+: shift-arg ( -- reg ) RCX ;
+: div-arg ( -- reg ) RAX ;
+: mod-arg ( -- reg ) RDX ;
+: temp0 ( -- reg ) RAX ;
+: temp1 ( -- reg ) RCX ;
+: temp2 ( -- reg ) RDX ;
+: temp3 ( -- reg ) RBX ;
+: pic-tail-reg ( -- reg ) RBX ;
+: return-reg ( -- reg ) RAX ;
+: nv-reg ( -- reg ) RBX ;
+: stack-reg ( -- reg ) RSP ;
+: frame-reg ( -- reg ) RBP ;
+: link-reg ( -- reg ) R11 ;
+: ctx-reg ( -- reg ) R12 ;
+: vm-reg ( -- reg ) R13 ;
+: ds-reg ( -- reg ) R14 ;
+: rs-reg ( -- reg ) R15 ;
+: fixnum>slot@ ( -- ) temp0 1 SAR ;
+: rex-length ( -- n ) 1 ;
+
+: jit-call ( name -- )
+    RAX 0 MOV f rc-absolute-cell rel-dlsym
+    RAX CALL ;
+
+[
+    pic-tail-reg 5 [RIP+] LEA
+    0 JMP f rc-relative rel-word-pic-tail
+] jit-word-jump jit-define
+
+: jit-load-vm ( -- )
+    ! no-op on x86-64. in factor contexts vm-reg always contains the
+    ! vm pointer.
+    ;
+
+: jit-load-context ( -- )
+    ctx-reg vm-reg vm-context-offset [+] MOV ;
+
+: jit-save-context ( -- )
+    jit-load-context
+    R11 RSP -8 [+] LEA
+    ctx-reg context-callstack-top-offset [+] R11 MOV
+    ctx-reg context-datastack-offset [+] ds-reg MOV
+    ctx-reg context-retainstack-offset [+] rs-reg MOV ;
+
+: jit-restore-context ( -- )
+    ds-reg ctx-reg context-datastack-offset [+] MOV
+    rs-reg ctx-reg context-retainstack-offset [+] MOV ;
+
+[
+    ! ctx-reg is preserved across the call because it is non-volatile
+    ! in the C ABI
+    jit-save-context
+    ! call the primitive
+    arg1 vm-reg MOV
+    RAX 0 MOV f f rc-absolute-cell rel-dlsym
+    RAX CALL
+    jit-restore-context
+] jit-primitive jit-define
+
+: jit-jump-quot ( -- ) arg1 quot-entry-point-offset [+] JMP ;
+
+: jit-call-quot ( -- ) arg1 quot-entry-point-offset [+] CALL ;
+
+[
+    arg2 arg1 MOV
+    arg1 vm-reg MOV
+    "begin_callback" jit-call
+
+    ! call the quotation
+    arg1 return-reg MOV
+    jit-call-quot
+
+    arg1 vm-reg MOV
+    "end_callback" jit-call
+] \ c-to-factor define-sub-primitive
+
+: signal-handler-save-regs ( -- regs )
+    { RAX RCX RDX RBX RBP RSI RDI R8 R9 R10 R11 R12 R13 R14 R15 } ;
+
+[
+    arg1 ds-reg [] MOV
+    ds-reg bootstrap-cell SUB
+]
+[ jit-call-quot ]
+[ jit-jump-quot ]
+\ (call) define-combinator-primitive
+
+[
+    ! Unwind stack frames
+    RSP arg2 MOV
+
+    ! Load VM pointer into vm-reg, since we're entering from
+    ! C code
+    vm-reg 0 MOV 0 rc-absolute-cell rel-vm
+
+    ! Load ds and rs registers
+    jit-load-context
+    jit-restore-context
+
+    ! Clear the fault flag
+    vm-reg vm-fault-flag-offset [+] 0 MOV
+
+    ! Call quotation
+    jit-jump-quot
+] \ unwind-native-frames define-sub-primitive
+
+[
+    RSP 2 SUB
+    RSP [] FNSTCW
+    FNINIT
+    AX RSP [] MOV
+    RSP 2 ADD
+] \ fpu-state define-sub-primitive
+
+[
+    RSP 2 SUB
+    RSP [] arg1 16-bit-version-of MOV
+    RSP [] FLDCW
+    RSP 2 ADD
+] \ set-fpu-state define-sub-primitive
+
+[
+    ! Load callstack object
+    arg4 ds-reg [] MOV
+    ds-reg bootstrap-cell SUB
+    ! Get ctx->callstack_bottom
+    jit-load-context
+    arg1 ctx-reg context-callstack-bottom-offset [+] MOV
+    ! Get top of callstack object -- 'src' for memcpy
+    arg2 arg4 callstack-top-offset [+] LEA
+    ! Get callstack length, in bytes --- 'len' for memcpy
+    arg3 arg4 callstack-length-offset [+] MOV
+    arg3 tag-bits get SHR
+    ! Compute new stack pointer -- 'dst' for memcpy
+    arg1 arg3 SUB
+    ! Install new stack pointer
+    RSP arg1 MOV
+    ! Call memcpy; arguments are now in the correct registers
+    ! Create register shadow area for Win64
+    RSP 32 SUB
+    "factor_memcpy" jit-call
+    ! Tear down register shadow area
+    RSP 32 ADD
+    ! Return with new callstack
+    0 RET
+] \ set-callstack define-sub-primitive
+
+[
+    jit-save-context
+    arg2 vm-reg MOV
+    "lazy_jit_compile" jit-call
+    arg1 return-reg MOV
+]
+[ return-reg quot-entry-point-offset [+] CALL ]
+[ jit-jump-quot ]
+\ lazy-jit-compile define-combinator-primitive
+
+[
+    temp2 0xffffffff MOV f rc-absolute-cell rel-literal
+    temp1 temp2 CMP
+] pic-check-tuple jit-define
+
+! Inline cache miss entry points
+: jit-load-return-address ( -- )
+    RBX RSP stack-frame-size bootstrap-cell - [+] MOV ;
+
+! These are always in tail position with an existing stack
+! frame, and the stack. The frame setup takes this into account.
+: jit-inline-cache-miss ( -- )
+    jit-save-context
+    arg1 RBX MOV
+    arg2 vm-reg MOV
+    RAX 0 MOV rc-absolute-cell rel-inline-cache-miss
+    RAX CALL
+    jit-load-context
+    jit-restore-context ;
+
+[ jit-load-return-address jit-inline-cache-miss ]
+[ RAX CALL ]
+[ RAX JMP ]
+\ inline-cache-miss define-combinator-primitive
+
+[ jit-inline-cache-miss ]
+[ RAX CALL ]
+[ RAX JMP ]
+\ inline-cache-miss-tail define-combinator-primitive
+
+! Overflowing fixnum arithmetic
+: jit-overflow ( insn func -- )
+    ds-reg 8 SUB
+    jit-save-context
+    arg1 ds-reg [] MOV
+    arg2 ds-reg 8 [+] MOV
+    arg3 arg1 MOV
+    [ [ arg3 arg2 ] dip call ] dip
+    ds-reg [] arg3 MOV
+    [ JNO ]
+    [ arg3 vm-reg MOV jit-call ]
+    jit-conditional ; inline
+
+[ [ ADD ] "overflow_fixnum_add" jit-overflow ] \ fixnum+ define-sub-primitive
+
+[ [ SUB ] "overflow_fixnum_subtract" jit-overflow ] \ fixnum- define-sub-primitive
+
+[
+    ds-reg 8 SUB
+    jit-save-context
+    RCX ds-reg [] MOV
+    RBX ds-reg 8 [+] MOV
+    RBX tag-bits get SAR
+    RAX RCX MOV
+    RBX IMUL
+    ds-reg [] RAX MOV
+    [ JNO ]
+    [
+        arg1 RCX MOV
+        arg1 tag-bits get SAR
+        arg2 RBX MOV
+        arg3 vm-reg MOV
+        "overflow_fixnum_multiply" jit-call
+    ]
+    jit-conditional
+] \ fixnum* define-sub-primitive
+
+! Contexts
+: jit-switch-context ( reg -- )
+    ! Push a bogus return address so the GC can track this frame back
+    ! to the owner
+    0 CALL
+
+    ! Make the new context the current one
+    ctx-reg swap MOV
+    vm-reg vm-context-offset [+] ctx-reg MOV
+
+    ! Load new stack pointer
+    RSP ctx-reg context-callstack-top-offset [+] MOV
+
+    ! Load new ds, rs registers
+    jit-restore-context
+
+    ctx-reg jit-update-tib ;
+
+: jit-pop-context-and-param ( -- )
+    arg1 ds-reg [] MOV
+    arg1 arg1 alien-offset [+] MOV
+    arg2 ds-reg -8 [+] MOV
+    ds-reg 16 SUB ;
+
+: jit-push-param ( -- )
+    ds-reg 8 ADD
+    ds-reg [] arg2 MOV ;
+
+: jit-set-context ( -- )
+    jit-pop-context-and-param
+    jit-save-context
+    arg1 jit-switch-context
+    RSP 8 ADD
+    jit-push-param ;
+
+[ jit-set-context ] \ (set-context) define-sub-primitive
+
+: jit-pop-quot-and-param ( -- )
+    arg1 ds-reg [] MOV
+    arg2 ds-reg -8 [+] MOV
+    ds-reg 16 SUB ;
+
+: jit-start-context ( -- )
+    ! Create the new context in return-reg. Have to save context
+    ! twice, first before calling new_context() which may GC,
+    ! and again after popping the two parameters from the stack.
+    jit-save-context
+    arg1 vm-reg MOV
+    "new_context" jit-call
+
+    jit-pop-quot-and-param
+    jit-save-context
+    return-reg jit-switch-context
+    jit-push-param
+    jit-jump-quot ;
+
+[ jit-start-context ] \ (start-context) define-sub-primitive
+
+: jit-delete-current-context ( -- )
+    jit-load-context
+    arg1 vm-reg MOV
+    arg2 ctx-reg MOV
+    "delete_context" jit-call ;
+
+[
+    jit-delete-current-context
+    jit-set-context
+] \ (set-context-and-delete) define-sub-primitive
+
+: jit-start-context-and-delete ( -- )
+    jit-load-context
+    arg1 vm-reg MOV
+    arg2 ctx-reg MOV
+    "reset_context" jit-call
+
+    jit-pop-quot-and-param
+    ctx-reg jit-switch-context
+    jit-push-param
+    jit-jump-quot ;
+
+[
+    0 [RIP+] EAX MOV rc-relative rel-safepoint
+] \ jit-safepoint jit-define
+
+[
+    jit-start-context-and-delete
+] \ (start-context-and-delete) define-sub-primitive
diff --git a/basis/bootstrap/assembler/x86.64.unix.factor b/basis/bootstrap/assembler/x86.64.unix.factor
new file mode 100644 (file)
index 0000000..2b66555
--- /dev/null
@@ -0,0 +1,24 @@
+! Copyright (C) 2008 Slava Pestov.
+! See http://factorcode.org/license.txt for BSD license.
+USING: bootstrap.image.private cpu.x86.assembler
+cpu.x86.assembler.operands kernel layouts namespaces parser
+sequences system vocabs ;
+IN: bootstrap.x86
+
+: leaf-stack-frame-size ( -- n ) 2 bootstrap-cells ;
+: signal-handler-stack-frame-size ( -- n ) 20 bootstrap-cells ;
+: stack-frame-size ( -- n ) 4 bootstrap-cells ;
+: nv-regs ( -- seq ) { RBX R12 R13 R14 R15 } ;
+: volatile-regs ( -- seq ) { RAX RCX RDX RSI RDI R8 R9 R10 R11 } ;
+
+! The first four parameter registers according to the Unix 64bit
+! calling convention.
+: arg1 ( -- reg ) RDI ;
+: arg2 ( -- reg ) RSI ;
+: arg3 ( -- reg ) RDX ;
+: arg4 ( -- reg ) RCX ;
+: red-zone-size ( -- n ) 128 ;
+
+<< "vocab:bootstrap/assembler/x86.unix.factor" parse-file suffix! >> call
+<< "vocab:bootstrap/assembler/x86.64.factor" parse-file suffix! >> call
+<< "vocab:bootstrap/assembler/x86.factor" parse-file suffix! >> call
diff --git a/basis/bootstrap/assembler/x86.64.windows.factor b/basis/bootstrap/assembler/x86.64.windows.factor
new file mode 100644 (file)
index 0000000..6cec39e
--- /dev/null
@@ -0,0 +1,30 @@
+! Copyright (C) 2008 Slava Pestov.
+! See http://factorcode.org/license.txt for BSD license.
+USING: bootstrap.image.private kernel namespaces system layouts
+vocabs sequences cpu.x86.assembler parser
+cpu.x86.assembler.operands ;
+IN: bootstrap.x86
+
+DEFER: stack-reg
+
+: leaf-stack-frame-size ( -- n ) 2 bootstrap-cells ;
+: signal-handler-stack-frame-size ( -- n ) 24 bootstrap-cells ;
+: stack-frame-size ( -- n ) 8 bootstrap-cells ;
+: nv-regs ( -- seq ) { RBX RSI RDI R12 R13 R14 R15 } ;
+: volatile-regs ( -- seq ) { RAX RCX RDX R8 R9 R10 R11 } ;
+: arg1 ( -- reg ) RCX ;
+: arg2 ( -- reg ) RDX ;
+: arg3 ( -- reg ) R8 ;
+: arg4 ( -- reg ) R9 ;
+
+: tib-segment ( -- ) GS ;
+: tib-temp ( -- reg ) R11 ;
+
+: jit-install-seh ( -- ) stack-reg bootstrap-cell ADD ;
+: jit-update-seh ( ctx-reg -- ) drop ;
+
+: red-zone-size ( -- n ) 0 ;
+
+<< "vocab:bootstrap/assembler/x86.windows.factor" parse-file suffix! >> call
+<< "vocab:bootstrap/assembler/x86.64.factor" parse-file suffix! >> call
+<< "vocab:bootstrap/assembler/x86.factor" parse-file suffix! >> call
diff --git a/basis/bootstrap/assembler/x86.factor b/basis/bootstrap/assembler/x86.factor
new file mode 100644 (file)
index 0000000..bf8d346
--- /dev/null
@@ -0,0 +1,649 @@
+! Copyright (C) 2007, 2011 Slava Pestov.
+! See http://factorcode.org/license.txt for BSD license.
+USING: bootstrap.image.private compiler.constants
+compiler.codegen.relocation compiler.units cpu.x86.assembler
+cpu.x86.assembler.operands kernel kernel.private layouts
+locals locals.backend make math math.private namespaces sequences
+slots.private strings.private vocabs ;
+IN: bootstrap.x86
+
+big-endian off
+
+! C to Factor entry point
+[
+    ! Optimizing compiler's side of callback accesses
+    ! arguments that are on the stack via the frame pointer.
+    ! On x86-32 fastcall, and x86-64, some arguments are passed
+    ! in registers, and so the only registers that are safe for
+    ! use here are frame-reg, nv-reg and vm-reg.
+    frame-reg PUSH
+    frame-reg stack-reg MOV
+
+    ! Save all non-volatile registers
+    nv-regs [ PUSH ] each
+
+    jit-save-tib
+
+    ! Load VM into vm-reg
+    vm-reg 0 MOV 0 rc-absolute-cell rel-vm
+
+    ! Save old context
+    nv-reg vm-reg vm-context-offset [+] MOV
+    nv-reg PUSH
+
+    ! Switch over to the spare context
+    nv-reg vm-reg vm-spare-context-offset [+] MOV
+    vm-reg vm-context-offset [+] nv-reg MOV
+
+    ! Save C callstack pointer
+    nv-reg context-callstack-save-offset [+] stack-reg MOV
+
+    ! Load Factor stack pointers
+    stack-reg nv-reg context-callstack-bottom-offset [+] MOV
+    nv-reg jit-update-tib
+    jit-install-seh
+
+    rs-reg nv-reg context-retainstack-offset [+] MOV
+    ds-reg nv-reg context-datastack-offset [+] MOV
+
+    ! Call into Factor code
+    link-reg 0 MOV f rc-absolute-cell rel-word
+    link-reg CALL
+
+    ! Load VM into vm-reg; only needed on x86-32, but doesn't
+    ! hurt on x86-64
+    vm-reg 0 MOV 0 rc-absolute-cell rel-vm
+
+    ! Load C callstack pointer
+    nv-reg vm-reg vm-context-offset [+] MOV
+    stack-reg nv-reg context-callstack-save-offset [+] MOV
+
+    ! Load old context
+    nv-reg POP
+    vm-reg vm-context-offset [+] nv-reg MOV
+
+    ! Restore non-volatile registers
+    jit-restore-tib
+
+    nv-regs <reversed> [ POP ] each
+
+    frame-reg POP
+
+    ! Callbacks which return structs, or use stdcall/fastcall/thiscall,
+    ! need a parameter here.
+
+    ! See the comment for M\ x86.32 stack-cleanup in cpu.x86.32
+    0xffff RET f rc-absolute-2 rel-untagged
+] callback-stub jit-define
+
+[
+    ! load literal
+    temp0 0 MOV f rc-absolute-cell rel-literal
+    ! increment datastack pointer
+    ds-reg bootstrap-cell ADD
+    ! store literal on datastack
+    ds-reg [] temp0 MOV
+] jit-push jit-define
+
+[
+    0 CALL f rc-relative rel-word-pic
+] jit-word-call jit-define
+
+! The *-signal-handler subprimitives are special-cased in vm/quotations.cpp
+! not to trigger generation of a stack frame, so they can
+! peform their own prolog/epilog preserving registers.
+
+: jit-signal-handler-prolog ( -- )
+    ! minus a cell each for flags, return address
+    ! use LEA so we don't dirty flags
+    stack-reg stack-reg signal-handler-stack-frame-size
+    2 bootstrap-cells - neg [+] LEA
+
+    signal-handler-save-regs
+    [| r i | stack-reg i bootstrap-cells [+] r MOV ] each-index
+
+    PUSHF
+
+    jit-load-vm ;
+
+: jit-signal-handler-epilog ( -- )
+    POPF
+
+    signal-handler-save-regs
+    [| r i | r stack-reg i bootstrap-cells [+] MOV ] each-index
+
+    stack-reg stack-reg signal-handler-stack-frame-size
+    2 bootstrap-cells - [+] LEA ;
+
+[| |
+    jit-signal-handler-prolog
+    jit-save-context
+    temp0 vm-reg vm-signal-handler-addr-offset [+] MOV
+    temp0 CALL
+    jit-signal-handler-epilog
+    0 RET
+] \ signal-handler define-sub-primitive
+
+[| |
+    jit-signal-handler-prolog
+    jit-save-context
+    temp0 vm-reg vm-signal-handler-addr-offset [+] MOV
+    temp0 CALL
+    jit-signal-handler-epilog
+    ! Pop the fake leaf frame along with our return address
+    leaf-stack-frame-size bootstrap-cell - RET
+] \ leaf-signal-handler define-sub-primitive
+
+[| |
+    jit-signal-handler-prolog
+    temp0 vm-reg vm-signal-handler-addr-offset [+] MOV
+    temp0 CALL
+    jit-signal-handler-epilog
+    red-zone-size RET
+] \ ffi-signal-handler define-sub-primitive
+
+[| |
+    jit-signal-handler-prolog
+    temp0 vm-reg vm-signal-handler-addr-offset [+] MOV
+    temp0 CALL
+    jit-signal-handler-epilog
+    red-zone-size 16 bootstrap-cell - + RET
+] \ ffi-leaf-signal-handler define-sub-primitive
+
+[
+    ! load boolean
+    temp0 ds-reg [] MOV
+    ! pop boolean
+    ds-reg bootstrap-cell SUB
+    ! compare boolean with f
+    temp0 \ f type-number CMP
+    ! jump to true branch if not equal
+    0 JNE f rc-relative rel-word
+    ! jump to false branch if equal
+    0 JMP f rc-relative rel-word
+] jit-if jit-define
+
+: jit->r ( -- )
+    rs-reg bootstrap-cell ADD
+    temp0 ds-reg [] MOV
+    ds-reg bootstrap-cell SUB
+    rs-reg [] temp0 MOV ;
+
+: jit-2>r ( -- )
+    rs-reg 2 bootstrap-cells ADD
+    temp0 ds-reg [] MOV
+    temp1 ds-reg -1 bootstrap-cells [+] MOV
+    ds-reg 2 bootstrap-cells SUB
+    rs-reg [] temp0 MOV
+    rs-reg -1 bootstrap-cells [+] temp1 MOV ;
+
+: jit-3>r ( -- )
+    rs-reg 3 bootstrap-cells ADD
+    temp0 ds-reg [] MOV
+    temp1 ds-reg -1 bootstrap-cells [+] MOV
+    temp2 ds-reg -2 bootstrap-cells [+] MOV
+    ds-reg 3 bootstrap-cells SUB
+    rs-reg [] temp0 MOV
+    rs-reg -1 bootstrap-cells [+] temp1 MOV
+    rs-reg -2 bootstrap-cells [+] temp2 MOV ;
+
+: jit-r> ( -- )
+    ds-reg bootstrap-cell ADD
+    temp0 rs-reg [] MOV
+    rs-reg bootstrap-cell SUB
+    ds-reg [] temp0 MOV ;
+
+: jit-2r> ( -- )
+    ds-reg 2 bootstrap-cells ADD
+    temp0 rs-reg [] MOV
+    temp1 rs-reg -1 bootstrap-cells [+] MOV
+    rs-reg 2 bootstrap-cells SUB
+    ds-reg [] temp0 MOV
+    ds-reg -1 bootstrap-cells [+] temp1 MOV ;
+
+: jit-3r> ( -- )
+    ds-reg 3 bootstrap-cells ADD
+    temp0 rs-reg [] MOV
+    temp1 rs-reg -1 bootstrap-cells [+] MOV
+    temp2 rs-reg -2 bootstrap-cells [+] MOV
+    rs-reg 3 bootstrap-cells SUB
+    ds-reg [] temp0 MOV
+    ds-reg -1 bootstrap-cells [+] temp1 MOV
+    ds-reg -2 bootstrap-cells [+] temp2 MOV ;
+
+[
+    jit->r
+    0 CALL f rc-relative rel-word
+    jit-r>
+] jit-dip jit-define
+
+[
+    jit-2>r
+    0 CALL f rc-relative rel-word
+    jit-2r>
+] jit-2dip jit-define
+
+[
+    jit-3>r
+    0 CALL f rc-relative rel-word
+    jit-3r>
+] jit-3dip jit-define
+
+[
+    ! load from stack
+    temp0 ds-reg [] MOV
+    ! pop stack
+    ds-reg bootstrap-cell SUB
+]
+[ temp0 word-entry-point-offset [+] CALL ]
+[ temp0 word-entry-point-offset [+] JMP ]
+\ (execute) define-combinator-primitive
+
+[
+    temp0 ds-reg [] MOV
+    ds-reg bootstrap-cell SUB
+    temp0 word-entry-point-offset [+] JMP
+] jit-execute jit-define
+
+[
+    stack-reg stack-frame-size bootstrap-cell - SUB
+] jit-prolog jit-define
+
+[
+    stack-reg stack-frame-size bootstrap-cell - ADD
+] jit-epilog jit-define
+
+[ 0 RET ] jit-return jit-define
+
+! ! ! Polymorphic inline caches
+
+! The PIC stubs are not permitted to touch pic-tail-reg.
+
+! Load a value from a stack position
+[
+    temp1 ds-reg 0x7f [+] MOV f rc-absolute-1 rel-untagged
+] pic-load jit-define
+
+[ temp1 tag-mask get AND ] pic-tag jit-define
+
+[
+    temp0 temp1 MOV
+    temp1 tag-mask get AND
+    temp1 tuple type-number CMP
+    [ JNE ]
+    [ temp1 temp0 tuple-class-offset [+] MOV ]
+    jit-conditional
+] pic-tuple jit-define
+
+[
+    temp1 0x7f CMP f rc-absolute-1 rel-untagged
+] pic-check-tag jit-define
+
+[ 0 JE f rc-relative rel-word ] pic-hit jit-define
+
+! ! ! Megamorphic caches
+
+[
+    ! class = ...
+    temp0 temp1 MOV
+    temp1 tag-mask get AND
+    temp1 tag-bits get SHL
+    temp1 tuple type-number tag-fixnum CMP
+    [ JNE ]
+    [ temp1 temp0 tuple-class-offset [+] MOV ]
+    jit-conditional
+    ! cache = ...
+    temp0 0 MOV f rc-absolute-cell rel-literal
+    ! key = hashcode(class)
+    temp2 temp1 MOV
+    bootstrap-cell 4 = [ temp2 1 SHR ] when
+    ! key &= cache.length - 1
+    temp2 mega-cache-size get 1 - bootstrap-cell * AND
+    ! cache += array-start-offset
+    temp0 array-start-offset ADD
+    ! cache += key
+    temp0 temp2 ADD
+    ! if(get(cache) == class)
+    temp0 [] temp1 CMP
+    [ JNE ]
+    [
+        ! megamorphic_cache_hits++
+        temp1 0 MOV rc-absolute-cell rel-megamorphic-cache-hits
+        temp1 [] 1 ADD
+        ! goto get(cache + bootstrap-cell)
+        temp0 temp0 bootstrap-cell [+] MOV
+        temp0 word-entry-point-offset [+] JMP
+        ! fall-through on miss
+    ] jit-conditional
+] mega-lookup jit-define
+
+! ! ! Sub-primitives
+
+! Objects
+[
+    ! load from stack
+    temp0 ds-reg [] MOV
+    ! compute tag
+    temp0 tag-mask get AND
+    ! tag the tag
+    temp0 tag-bits get SHL
+    ! push to stack
+    ds-reg [] temp0 MOV
+] \ tag define-sub-primitive
+
+[
+    ! load slot number
+    temp0 ds-reg [] MOV
+    ! adjust stack pointer
+    ds-reg bootstrap-cell SUB
+    ! load object
+    temp1 ds-reg [] MOV
+    ! turn slot number into offset
+    fixnum>slot@
+    ! mask off tag
+    temp1 tag-bits get SHR
+    temp1 tag-bits get SHL
+    ! load slot value
+    temp0 temp1 temp0 [+] MOV
+    ! push to stack
+    ds-reg [] temp0 MOV
+] \ slot define-sub-primitive
+
+[
+    ! load string index from stack
+    temp0 ds-reg bootstrap-cell neg [+] MOV
+    temp0 tag-bits get SHR
+    ! load string from stack
+    temp1 ds-reg [] MOV
+    ! load character
+    temp0 8-bit-version-of temp0 temp1 string-offset [++] MOV
+    temp0 temp0 8-bit-version-of MOVZX
+    temp0 tag-bits get SHL
+    ! store character to stack
+    ds-reg bootstrap-cell SUB
+    ds-reg [] temp0 MOV
+] \ string-nth-fast define-sub-primitive
+
+! Shufflers
+[
+    ds-reg bootstrap-cell SUB
+] \ drop define-sub-primitive
+
+[
+    ds-reg 2 bootstrap-cells SUB
+] \ 2drop define-sub-primitive
+
+[
+    ds-reg 3 bootstrap-cells SUB
+] \ 3drop define-sub-primitive
+
+[
+    ds-reg 4 bootstrap-cells SUB
+] \ 4drop define-sub-primitive
+
+[
+    temp0 ds-reg [] MOV
+    ds-reg bootstrap-cell ADD
+    ds-reg [] temp0 MOV
+] \ dup define-sub-primitive
+
+[
+    temp0 ds-reg [] MOV
+    temp1 ds-reg bootstrap-cell neg [+] MOV
+    ds-reg 2 bootstrap-cells ADD
+    ds-reg [] temp0 MOV
+    ds-reg bootstrap-cell neg [+] temp1 MOV
+] \ 2dup define-sub-primitive
+
+[
+    temp0 ds-reg [] MOV
+    temp1 ds-reg -1 bootstrap-cells [+] MOV
+    temp3 ds-reg -2 bootstrap-cells [+] MOV
+    ds-reg 3 bootstrap-cells ADD
+    ds-reg [] temp0 MOV
+    ds-reg -1 bootstrap-cells [+] temp1 MOV
+    ds-reg -2 bootstrap-cells [+] temp3 MOV
+] \ 3dup define-sub-primitive
+
+[
+    temp0 ds-reg [] MOV
+    temp1 ds-reg -1 bootstrap-cells [+] MOV
+    temp2 ds-reg -2 bootstrap-cells [+] MOV
+    temp3 ds-reg -3 bootstrap-cells [+] MOV
+    ds-reg 4 bootstrap-cells ADD
+    ds-reg [] temp0 MOV
+    ds-reg -1 bootstrap-cells [+] temp1 MOV
+    ds-reg -2 bootstrap-cells [+] temp2 MOV
+    ds-reg -3 bootstrap-cells [+] temp3 MOV
+] \ 4dup define-sub-primitive
+
+[
+    temp0 ds-reg [] MOV
+    ds-reg bootstrap-cell SUB
+    ds-reg [] temp0 MOV
+] \ nip define-sub-primitive
+
+[
+    temp0 ds-reg [] MOV
+    ds-reg 2 bootstrap-cells SUB
+    ds-reg [] temp0 MOV
+] \ 2nip define-sub-primitive
+
+[
+    temp0 ds-reg -1 bootstrap-cells [+] MOV
+    ds-reg bootstrap-cell ADD
+    ds-reg [] temp0 MOV
+] \ over define-sub-primitive
+
+[
+    temp0 ds-reg -2 bootstrap-cells [+] MOV
+    ds-reg bootstrap-cell ADD
+    ds-reg [] temp0 MOV
+] \ pick define-sub-primitive
+
+[
+    temp0 ds-reg [] MOV
+    temp1 ds-reg -1 bootstrap-cells [+] MOV
+    ds-reg [] temp1 MOV
+    ds-reg bootstrap-cell ADD
+    ds-reg [] temp0 MOV
+] \ dupd define-sub-primitive
+
+[
+    temp0 ds-reg [] MOV
+    temp1 ds-reg bootstrap-cell neg [+] MOV
+    ds-reg bootstrap-cell neg [+] temp0 MOV
+    ds-reg [] temp1 MOV
+] \ swap define-sub-primitive
+
+[
+    temp0 ds-reg -1 bootstrap-cells [+] MOV
+    temp1 ds-reg -2 bootstrap-cells [+] MOV
+    ds-reg -2 bootstrap-cells [+] temp0 MOV
+    ds-reg -1 bootstrap-cells [+] temp1 MOV
+] \ swapd define-sub-primitive
+
+[
+    temp0 ds-reg [] MOV
+    temp1 ds-reg -1 bootstrap-cells [+] MOV
+    temp3 ds-reg -2 bootstrap-cells [+] MOV
+    ds-reg -2 bootstrap-cells [+] temp1 MOV
+    ds-reg -1 bootstrap-cells [+] temp0 MOV
+    ds-reg [] temp3 MOV
+] \ rot define-sub-primitive
+
+[
+    temp0 ds-reg [] MOV
+    temp1 ds-reg -1 bootstrap-cells [+] MOV
+    temp3 ds-reg -2 bootstrap-cells [+] MOV
+    ds-reg -2 bootstrap-cells [+] temp0 MOV
+    ds-reg -1 bootstrap-cells [+] temp3 MOV
+    ds-reg [] temp1 MOV
+] \ -rot define-sub-primitive
+
+[ jit->r ] \ load-local define-sub-primitive
+
+! Comparisons
+: jit-compare ( insn -- )
+    ! load t
+    temp3 0 MOV t rc-absolute-cell rel-literal
+    ! load f
+    temp1 \ f type-number MOV
+    ! load first value
+    temp0 ds-reg [] MOV
+    ! adjust stack pointer
+    ds-reg bootstrap-cell SUB
+    ! compare with second value
+    ds-reg [] temp0 CMP
+    ! move t if true
+    [ temp1 temp3 ] dip execute( dst src -- )
+    ! store
+    ds-reg [] temp1 MOV ;
+
+: define-jit-compare ( insn word -- )
+    [ [ jit-compare ] curry ] dip define-sub-primitive ;
+
+\ CMOVE \ eq? define-jit-compare
+\ CMOVGE \ fixnum>= define-jit-compare
+\ CMOVLE \ fixnum<= define-jit-compare
+\ CMOVG \ fixnum> define-jit-compare
+\ CMOVL \ fixnum< define-jit-compare
+
+! Math
+: jit-math ( insn -- )
+    ! load second input
+    temp0 ds-reg [] MOV
+    ! pop stack
+    ds-reg bootstrap-cell SUB
+    ! compute result
+    [ ds-reg [] temp0 ] dip execute( dst src -- ) ;
+
+[ \ ADD jit-math ] \ fixnum+fast define-sub-primitive
+
+[ \ SUB jit-math ] \ fixnum-fast define-sub-primitive
+
+[
+    ! load second input
+    temp0 ds-reg [] MOV
+    ! pop stack
+    ds-reg bootstrap-cell SUB
+    ! load first input
+    temp1 ds-reg [] MOV
+    ! untag second input
+    temp0 tag-bits get SAR
+    ! multiply
+    temp0 temp1 IMUL2
+    ! push result
+    ds-reg [] temp0 MOV
+] \ fixnum*fast define-sub-primitive
+
+[ \ AND jit-math ] \ fixnum-bitand define-sub-primitive
+
+[ \ OR jit-math ] \ fixnum-bitor define-sub-primitive
+
+[ \ XOR jit-math ] \ fixnum-bitxor define-sub-primitive
+
+[
+    ! complement
+    ds-reg [] NOT
+    ! clear tag bits
+    ds-reg [] tag-mask get XOR
+] \ fixnum-bitnot define-sub-primitive
+
+[
+    ! load shift count
+    shift-arg ds-reg [] MOV
+    ! untag shift count
+    shift-arg tag-bits get SAR
+    ! adjust stack pointer
+    ds-reg bootstrap-cell SUB
+    ! load value
+    temp3 ds-reg [] MOV
+    ! make a copy
+    temp2 temp3 MOV
+    ! compute positive shift value in temp2
+    temp2 CL SHL
+    shift-arg NEG
+    ! compute negative shift value in temp3
+    temp3 CL SAR
+    temp3 tag-mask get bitnot AND
+    shift-arg 0 CMP
+    ! if shift count was negative, move temp0 to temp2
+    temp2 temp3 CMOVGE
+    ! push to stack
+    ds-reg [] temp2 MOV
+] \ fixnum-shift-fast define-sub-primitive
+
+: jit-fixnum-/mod ( -- )
+    ! load second parameter
+    temp1 ds-reg [] MOV
+    ! load first parameter
+    div-arg ds-reg bootstrap-cell neg [+] MOV
+    ! make a copy
+    mod-arg div-arg MOV
+    ! sign-extend
+    mod-arg bootstrap-cell-bits 1 - SAR
+    ! divide
+    temp1 IDIV ;
+
+[
+    jit-fixnum-/mod
+    ! adjust stack pointer
+    ds-reg bootstrap-cell SUB
+    ! push to stack
+    ds-reg [] mod-arg MOV
+] \ fixnum-mod define-sub-primitive
+
+[
+    jit-fixnum-/mod
+    ! adjust stack pointer
+    ds-reg bootstrap-cell SUB
+    ! tag it
+    div-arg tag-bits get SHL
+    ! push to stack
+    ds-reg [] div-arg MOV
+] \ fixnum/i-fast define-sub-primitive
+
+[
+    jit-fixnum-/mod
+    ! tag it
+    div-arg tag-bits get SHL
+    ! push to stack
+    ds-reg [] mod-arg MOV
+    ds-reg bootstrap-cell neg [+] div-arg MOV
+] \ fixnum/mod-fast define-sub-primitive
+
+[
+    temp0 ds-reg [] MOV
+    ds-reg bootstrap-cell SUB
+    temp0 ds-reg [] OR
+    temp0 tag-mask get TEST
+    temp0 \ f type-number MOV
+    temp1 1 tag-fixnum MOV
+    temp0 temp1 CMOVE
+    ds-reg [] temp0 MOV
+] \ both-fixnums? define-sub-primitive
+
+[
+    ! load local number
+    temp0 ds-reg [] MOV
+    ! turn local number into offset
+    fixnum>slot@
+    ! load local value
+    temp0 rs-reg temp0 [+] MOV
+    ! push to stack
+    ds-reg [] temp0 MOV
+] \ get-local define-sub-primitive
+
+[
+    ! load local count
+    temp0 ds-reg [] MOV
+    ! adjust stack pointer
+    ds-reg bootstrap-cell SUB
+    ! turn local number into offset
+    fixnum>slot@
+    ! decrement retain stack pointer
+    rs-reg temp0 SUB
+] \ drop-locals define-sub-primitive
+
+[ "bootstrap.x86" forget-vocab ] with-compilation-unit
diff --git a/basis/bootstrap/assembler/x86.unix.factor b/basis/bootstrap/assembler/x86.unix.factor
new file mode 100644 (file)
index 0000000..20dd738
--- /dev/null
@@ -0,0 +1,13 @@
+! Copyright (C) 2010 Slava Pestov.
+! See http://factorcode.org/license.txt for BSD license.
+USING: cpu.x86.assembler cpu.x86.assembler.operands kernel
+layouts ;
+IN: bootstrap.x86
+
+DEFER: stack-reg
+
+: jit-save-tib ( -- ) ;
+: jit-restore-tib ( -- ) ;
+: jit-update-tib ( ctx-reg -- ) drop ;
+: jit-install-seh ( -- ) stack-reg bootstrap-cell ADD ;
+: jit-update-seh ( ctx-reg -- ) drop ;
diff --git a/basis/bootstrap/assembler/x86.windows.factor b/basis/bootstrap/assembler/x86.windows.factor
new file mode 100644 (file)
index 0000000..b81c1eb
--- /dev/null
@@ -0,0 +1,32 @@
+! Copyright (C) 2010 Slava Pestov.
+! See http://factorcode.org/license.txt for BSD license.
+USING: bootstrap.image.private compiler.constants
+cpu.x86.assembler cpu.x86.assembler.operands kernel layouts
+locals parser sequences ;
+IN: bootstrap.x86
+
+: tib-exception-list-offset ( -- n ) 0 bootstrap-cells ;
+: tib-stack-base-offset ( -- n ) 1 bootstrap-cells ;
+: tib-stack-limit-offset ( -- n ) 2 bootstrap-cells ;
+
+: jit-save-tib ( -- )
+    tib-exception-list-offset [] tib-segment PUSH
+    tib-stack-base-offset [] tib-segment PUSH
+    tib-stack-limit-offset [] tib-segment PUSH ;
+
+: jit-restore-tib ( -- )
+    tib-stack-limit-offset [] tib-segment POP
+    tib-stack-base-offset [] tib-segment POP
+    tib-exception-list-offset [] tib-segment POP ;
+
+:: jit-update-tib ( ctx-reg -- )
+    ! There's a redundant load here because we're not allowed
+    ! to clobber ctx-reg. Clobbers tib-temp.
+    ! Save callstack base in TIB
+    tib-temp ctx-reg context-callstack-seg-offset [+] MOV
+    tib-temp tib-temp segment-end-offset [+] MOV
+    tib-stack-base-offset [] tib-temp tib-segment MOV
+    ! Save callstack limit in TIB
+    tib-temp ctx-reg context-callstack-seg-offset [+] MOV
+    tib-temp tib-temp segment-start-offset [+] MOV
+    tib-stack-limit-offset [] tib-temp tib-segment MOV ;
diff --git a/basis/cpu/ppc/32/linux/bootstrap.factor b/basis/cpu/ppc/32/linux/bootstrap.factor
deleted file mode 100644 (file)
index 7a4b6ac..0000000
+++ /dev/null
@@ -1,73 +0,0 @@
-! Copyright (C) 2011 Erik Charlebois.
-! See http://factorcode.org/license.txt for BSD license.
-USING: parser system kernel sequences math math.ranges
-cpu.ppc.assembler combinators compiler.constants
-bootstrap.image.private layouts namespaces ;
-IN: bootstrap.ppc
-
-4 \ cell set
-big-endian on
-
-: reserved-size ( -- n ) 24 ;
-: lr-save ( -- n ) 4 ;
-
-CONSTANT: ds-reg    14
-CONSTANT: rs-reg    15
-CONSTANT: vm-reg    16
-CONSTANT: ctx-reg   17
-CONSTANT: frame-reg 31
-: nv-int-regs ( -- seq ) 13 31 [a,b] ;
-
-: LOAD32 ( r n -- )
-    [ -16 shift 0xffff bitand LIS ]
-    [ [ dup ] dip 0xffff bitand ORI ] 2bi ;
-
-: jit-trap-null ( src -- ) drop ;
-: jit-load-vm ( dst -- )
-    0 LOAD32 0 rc-absolute-ppc-2/2 jit-vm ;
-: jit-load-dlsym ( dst string -- )
-    [ 0 LOAD32 ] dip rc-absolute-ppc-2/2 jit-dlsym ;
-: jit-load-dlsym-toc ( string -- ) drop ;
-: jit-load-vm-arg ( dst -- )
-    0 LOAD32 rc-absolute-ppc-2/2 rt-vm jit-rel ;
-: jit-load-entry-point-arg ( dst -- )
-    0 LOAD32 rc-absolute-ppc-2/2 rt-entry-point jit-rel ;
-: jit-load-this-arg ( dst -- )
-    0 LOAD32 rc-absolute-ppc-2/2 rt-this jit-rel ;
-: jit-load-literal-arg ( dst -- )
-    0 LOAD32 rc-absolute-ppc-2/2 rt-literal jit-rel ;
-: jit-load-dlsym-arg ( dst -- )
-    0 LOAD32 rc-absolute-ppc-2/2 rt-dlsym jit-rel ;
-: jit-load-dlsym-toc-arg ( -- ) ;
-: jit-load-here-arg ( dst -- )
-    0 LOAD32 rc-absolute-ppc-2/2 rt-here jit-rel ;
-: jit-load-megamorphic-cache-arg ( dst -- )
-    0 LOAD32 rc-absolute-ppc-2/2 rt-megamorphic-cache-hits jit-rel ;
-: jit-load-cell ( dst src offset -- ) LWZ ;
-: jit-load-cell-x ( dst src offset -- ) LWZX ;
-: jit-load-cell-update ( dst src offset -- ) LWZU ;
-: jit-save-cell ( dst src offset -- ) STW ;
-: jit-save-cell-x ( dst src offset -- ) STWX ;
-: jit-save-cell-update ( dst src offset -- ) STWU ;
-: jit-load-int ( dst src offset -- ) LWZ ;
-: jit-save-int ( dst src offset -- ) STW ;
-: jit-shift-tag-bits ( dst src -- ) tag-bits get SRAWI ;
-: jit-mask-tag-bits ( dst src -- ) tag-bits get CLRRWI ;
-: jit-shift-fixnum-slot ( dst src -- ) 2 SRAWI ;
-: jit-class-hashcode ( dst src -- ) 1 SRAWI ;
-: jit-shift-left-logical ( dst src n -- ) SLW ;
-: jit-shift-left-logical-imm ( dst src n -- ) SLWI ;
-: jit-shift-right-algebraic ( dst src n -- ) SRAW ;
-: jit-divide ( dst ra rb -- ) DIVW ;
-: jit-multiply-low ( dst ra rb -- ) MULLW ;
-: jit-multiply-low-ov-rc ( dst ra rb -- ) MULLWO. ;
-: jit-compare-cell ( cr ra rb -- ) CMPW ;
-: jit-compare-cell-imm ( cr ra imm -- ) CMPWI ;
-
-: cell-size ( -- n ) 4 ;
-: factor-area-size ( -- n ) 16 ;
-: param-size ( -- n ) 32 ;
-: saved-int-regs-size ( -- n ) 96 ;
-
-<< "vocab:cpu/ppc/bootstrap.factor" parse-file suffix! >>
-call
diff --git a/basis/cpu/ppc/64/linux/bootstrap.factor b/basis/cpu/ppc/64/linux/bootstrap.factor
deleted file mode 100644 (file)
index 8d2ded4..0000000
+++ /dev/null
@@ -1,80 +0,0 @@
-! Copyright (C) 2011 Erik Charlebois.
-! See http://factorcode.org/license.txt for BSD license.
-USING: parser system kernel sequences math math.ranges
-cpu.ppc.assembler combinators compiler.constants
-bootstrap.image.private layouts namespaces ;
-IN: bootstrap.ppc
-
-8 \ cell set
-big-endian on
-
-: reserved-size ( -- n ) 48 ;
-: lr-save ( -- n ) 16 ;
-
-CONSTANT: ds-reg    14
-CONSTANT: rs-reg    15
-CONSTANT: vm-reg    16
-CONSTANT: ctx-reg   17
-CONSTANT: frame-reg 31
-: nv-int-regs ( -- seq ) 13 31 [a,b] ;
-
-: LOAD64 ( r n -- )
-    [ dup ] dip {
-        [ nip -48 shift 0xffff bitand LIS ]
-        [ -32 shift 0xffff bitand ORI ]
-        [ drop 32 SLDI ]
-        [ -16 shift 0xffff bitand ORIS ]
-        [ 0xffff bitand ORI ]
-    } 3cleave ;
-
-: jit-trap-null ( src -- ) drop ;
-: jit-load-vm ( dst -- )
-    0 LOAD64 0 rc-absolute-ppc-2/2/2/2 jit-vm ;
-: jit-load-dlsym ( dst string -- )
-    [ 0 LOAD64 ] dip rc-absolute-ppc-2/2/2/2 jit-dlsym ;
-: jit-load-dlsym-toc ( string -- )
-    [ 2 0 LOAD64 ] dip rc-absolute-ppc-2/2/2/2 jit-dlsym-toc ;
-: jit-load-vm-arg ( dst -- )
-    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-vm jit-rel ;
-: jit-load-entry-point-arg ( dst -- )
-    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-entry-point jit-rel ;
-: jit-load-this-arg ( dst -- )
-    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-this jit-rel ;
-: jit-load-literal-arg ( dst -- )
-    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-literal jit-rel ;
-: jit-load-dlsym-arg ( dst -- )
-    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-dlsym jit-rel ;
-: jit-load-dlsym-toc-arg ( -- )
-    2 0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-dlsym-toc jit-rel ;
-: jit-load-here-arg ( dst -- )
-    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-here jit-rel ;
-: jit-load-megamorphic-cache-arg ( dst -- )
-    0 LOAD64 rc-absolute-ppc-2/2/2/2 rt-megamorphic-cache-hits jit-rel ;
-: jit-load-cell ( dst src offset -- ) LD ;
-: jit-load-cell-x ( dst src offset -- ) LDX ;
-: jit-load-cell-update ( dst src offset -- ) LDU ;
-: jit-save-cell ( dst src offset -- ) STD ;
-: jit-save-cell-x ( dst src offset -- ) STDX ;
-: jit-save-cell-update ( dst src offset -- ) STDU ;
-: jit-load-int ( dst src offset -- ) LD ;
-: jit-save-int ( dst src offset -- ) STD ;
-: jit-shift-tag-bits ( dst src -- ) tag-bits get SRADI ;
-: jit-mask-tag-bits ( dst src -- ) tag-bits get CLRRDI ;
-: jit-shift-fixnum-slot ( dst src -- ) 1 SRADI ;
-: jit-class-hashcode ( dst src -- ) 1 SRADI ;
-: jit-shift-left-logical ( dst src n -- ) SLD ;
-: jit-shift-left-logical-imm ( dst src n -- ) SLDI ;
-: jit-shift-right-algebraic ( dst src n -- ) SRAD ;
-: jit-divide ( dst ra rb -- ) DIVD ;
-: jit-multiply-low ( dst ra rb -- ) MULLD ;
-: jit-multiply-low-ov-rc ( dst ra rb -- ) MULLDO. ;
-: jit-compare-cell ( cr ra rb -- ) CMPD ;
-: jit-compare-cell-imm ( cr ra imm -- ) CMPDI ;
-
-: cell-size ( -- n ) 8 ;
-: factor-area-size ( -- n ) 32 ;
-: param-size ( -- n ) 64 ;
-: saved-int-regs-size ( -- n ) 192 ;
-
-<< "vocab:cpu/ppc/bootstrap.factor" parse-file suffix! >>
-call
diff --git a/basis/cpu/ppc/bootstrap.factor b/basis/cpu/ppc/bootstrap.factor
deleted file mode 100644 (file)
index c0f565e..0000000
+++ /dev/null
@@ -1,845 +0,0 @@
-! Copyright (C) 2011 Erik Charlebois
-! See http://factorcode.org/license.txt for BSD license.
-USING: bootstrap.image.private kernel kernel.private namespaces
-system cpu.ppc.assembler compiler.units compiler.constants math
-math.private math.ranges layouts words vocabs slots.private
-locals locals.backend generic.single.private fry sequences
-threads.private strings.private ;
-FROM: cpu.ppc.assembler => B ;
-IN: bootstrap.ppc
-
-: jit-call ( string -- )
-    dup
-    0 swap jit-load-dlsym
-    0 MTLR
-    jit-load-dlsym-toc
-    BLRL ;
-
-: jit-call-quot ( -- )
-    4 quot-entry-point-offset LI
-    4 3 4 jit-load-cell-x
-    4 MTLR
-    BLRL ;
-
-: jit-jump-quot ( -- )
-    4 quot-entry-point-offset LI
-    4 3 4 jit-load-cell-x
-    4 MTCTR
-    BCTR ;
-
-: stack-frame ( -- n )
-    reserved-size factor-area-size + 16 align ;
-
-: save-at ( m -- n ) reserved-size + param-size + ;
-
-: save-int ( reg off -- ) [ 1 ] dip save-at jit-save-int ;
-: save-fp  ( reg off -- ) [ 1 ] dip save-at STFD ;
-: save-vec ( reg offt -- ) save-at 11 swap LI 11 1 STVXL ;
-: restore-int ( reg off -- ) [ 1 ] dip save-at jit-load-int ;
-: restore-fp  ( reg off -- ) [ 1 ] dip save-at LFD ;
-: restore-vec ( reg offt -- ) save-at 11 swap LI 11 1 LVXL ;
-
-! Stop using intervals here.
-: nv-fp-regs  ( -- seq ) 14 31 [a,b] ;
-: nv-vec-regs ( -- seq ) 20 31 [a,b] ;
-
-: saved-fp-regs-size  ( -- n ) 144 ;
-: saved-vec-regs-size ( -- n ) 192 ;
-
-: callback-frame-size ( -- n )
-    reserved-size
-    param-size +
-    saved-int-regs-size +
-    saved-fp-regs-size +
-    saved-vec-regs-size +
-    16 align ;
-
-: old-context-save-offset ( -- n )
-    cell-size 20 * saved-fp-regs-size + saved-vec-regs-size + save-at ;
-
-[
-    ! Save old stack pointer
-    11 1 MR
-
-    0 MFLR                                           ! Get return address
-    0 1 lr-save jit-save-cell                        ! Stash return address
-    1 1 callback-frame-size neg jit-save-cell-update ! Bump stack pointer and set back chain
-
-    ! Save all non-volatile registers
-    nv-int-regs [ cell-size * save-int ] each-index
-    nv-fp-regs [ 8 * saved-int-regs-size + save-fp  ] each-index
-    ! nv-vec-regs [ 16 * saved-int-regs-size saved-fp-regs-size + + save-vec ] each-index
-
-    ! Stick old stack pointer in the frame register so callbacks
-    ! can access their arguments
-    frame-reg 11 MR
-
-    ! Load VM into vm-reg
-    vm-reg jit-load-vm-arg
-
-    ! Save old context
-    0 vm-reg vm-context-offset jit-load-cell
-    0 1 old-context-save-offset jit-save-cell
-
-    ! Switch over to the spare context
-    11 vm-reg vm-spare-context-offset jit-load-cell
-    11 vm-reg vm-context-offset jit-save-cell
-
-    ! Save C callstack pointer and load Factor callstack
-    1 11 context-callstack-save-offset jit-save-cell
-    1 11 context-callstack-bottom-offset jit-load-cell
-
-    ! Load new data and retain stacks
-    rs-reg 11 context-retainstack-offset jit-load-cell
-    ds-reg 11 context-datastack-offset jit-load-cell
-
-    ! Call into Factor code
-    0 jit-load-entry-point-arg
-    0 MTLR
-    BLRL
-
-    ! Load VM again, pointlessly
-    vm-reg jit-load-vm-arg
-
-    ! Load C callstack pointer
-    11 vm-reg vm-context-offset jit-load-cell
-    1 11 context-callstack-save-offset jit-load-cell
-
-    ! Load old context
-    0 1 old-context-save-offset jit-load-cell
-    0 vm-reg vm-context-offset jit-save-cell
-
-    ! Restore non-volatile registers
-    ! nv-vec-regs [ 16 * saved-int-regs-size saved-float-regs-size + + restore-vec ] each-index
-    nv-fp-regs [ 8 * saved-int-regs-size + restore-fp ] each-index
-    nv-int-regs [ cell-size * restore-int ] each-index
-
-    1 1 callback-frame-size ADDI ! Bump stack back up
-    0 1 lr-save jit-load-cell    ! Fetch return address
-    0 MTLR                       ! Set up return
-    BLR                          ! Branch back
-] callback-stub jit-define
-
-: jit-conditional* ( test-quot false-quot -- )
-    [ '[ 4 + @ ] ] dip jit-conditional ; inline
-
-: jit-load-context ( -- )
-    ctx-reg vm-reg vm-context-offset jit-load-cell ;
-
-: jit-save-context ( -- )
-    jit-load-context
-    1 ctx-reg context-callstack-top-offset jit-save-cell
-    ds-reg ctx-reg context-datastack-offset jit-save-cell
-    rs-reg ctx-reg context-retainstack-offset jit-save-cell ;
-
-: jit-restore-context ( -- )
-    ds-reg ctx-reg context-datastack-offset jit-load-cell
-    rs-reg ctx-reg context-retainstack-offset jit-load-cell ;
-
-[
-    12 jit-load-literal-arg
-    0 profile-count-offset LI
-    11 12 0 jit-load-cell-x
-    11 11 1 tag-fixnum ADDI
-    11 12 0 jit-save-cell-x
-    0 word-code-offset LI
-    11 12 0 jit-load-cell-x
-    11 11 compiled-header-size ADDI
-    11 MTCTR
-    BCTR
-] jit-profiling jit-define
-
-[
-    0 MFLR
-    0 1 lr-save jit-save-cell
-    0 jit-load-this-arg
-    0 1 cell-size 2 * neg jit-save-cell
-    0 stack-frame LI
-    0 1 cell-size 1 * neg jit-save-cell
-    1 1 stack-frame neg jit-save-cell-update
-] jit-prolog jit-define
-
-[
-    3 jit-load-literal-arg
-    3 ds-reg cell-size jit-save-cell-update
-] jit-push jit-define
-
-[
-    jit-save-context
-    3 vm-reg MR
-    4 jit-load-dlsym-arg
-    4 MTLR
-    jit-load-dlsym-toc-arg ! Restore the TOC/GOT
-    BLRL
-    jit-restore-context
-] jit-primitive jit-define
-
-[ 0 BL rc-relative-ppc-3-pc rt-entry-point-pic jit-rel ] jit-word-call jit-define
-
-[
-    6 jit-load-here-arg
-    0 B rc-relative-ppc-3-pc rt-entry-point-pic-tail jit-rel
-] jit-word-jump jit-define
-
-[
-    3 ds-reg 0 jit-load-cell
-    ds-reg dup cell-size SUBI
-    0 3 \ f type-number jit-compare-cell-imm
-    [ 0 swap BEQ ] [ 0 B rc-relative-ppc-3-pc rt-entry-point jit-rel ] jit-conditional*
-    0 B rc-relative-ppc-3-pc rt-entry-point jit-rel
-] jit-if jit-define
-
-: jit->r ( -- )
-    4 ds-reg 0 jit-load-cell
-    ds-reg dup cell-size SUBI
-    4 rs-reg cell-size jit-save-cell-update ;
-
-: jit-2>r ( -- )
-    4 ds-reg 0 jit-load-cell
-    5 ds-reg cell-size neg jit-load-cell
-    ds-reg dup 2 cell-size * SUBI
-    rs-reg dup 2 cell-size * ADDI
-    4 rs-reg 0 jit-save-cell
-    5 rs-reg cell-size neg jit-save-cell ;
-
-: jit-3>r ( -- )
-    4 ds-reg 0 jit-load-cell
-    5 ds-reg cell-size neg jit-load-cell
-    6 ds-reg cell-size neg 2 * jit-load-cell
-    ds-reg dup 3 cell-size * SUBI
-    rs-reg dup 3 cell-size * ADDI
-    4 rs-reg 0 jit-save-cell
-    5 rs-reg cell-size neg jit-save-cell
-    6 rs-reg cell-size neg 2 * jit-save-cell ;
-
-: jit-r> ( -- )
-    4 rs-reg 0 jit-load-cell
-    rs-reg dup cell-size SUBI
-    4 ds-reg cell-size jit-save-cell-update ;
-
-: jit-2r> ( -- )
-    4 rs-reg 0 jit-load-cell
-    5 rs-reg cell-size neg jit-load-cell
-    rs-reg dup 2 cell-size * SUBI
-    ds-reg dup 2 cell-size * ADDI
-    4 ds-reg 0 jit-save-cell
-    5 ds-reg cell-size neg jit-save-cell ;
-
-: jit-3r> ( -- )
-    4 rs-reg 0 jit-load-cell
-    5 rs-reg cell-size neg jit-load-cell
-    6 rs-reg cell-size neg 2 * jit-load-cell
-    rs-reg dup 3 cell-size * SUBI
-    ds-reg dup 3 cell-size * ADDI
-    4 ds-reg 0 jit-save-cell
-    5 ds-reg cell-size neg jit-save-cell
-    6 ds-reg cell-size neg 2 * jit-save-cell ;
-
-[
-    jit->r
-    0 BL rc-relative-ppc-3-pc rt-entry-point jit-rel
-    jit-r>
-] jit-dip jit-define
-
-[
-    jit-2>r
-    0 BL rc-relative-ppc-3-pc rt-entry-point jit-rel
-    jit-2r>
-] jit-2dip jit-define
-
-[
-    jit-3>r
-    0 BL rc-relative-ppc-3-pc rt-entry-point jit-rel
-    jit-3r>
-] jit-3dip jit-define
-
-[
-    1 1 stack-frame ADDI
-    0 1 lr-save jit-load-cell
-    0 MTLR
-] jit-epilog jit-define
-
-[ BLR ] jit-return jit-define
-
-! ! ! Polymorphic inline caches
-
-! Don't touch r6 here; it's used to pass the tail call site
-! address for tail PICs
-
-! Load a value from a stack position
-[
-    4 ds-reg 0 jit-load-cell rc-absolute-ppc-2 rt-untagged jit-rel
-] pic-load jit-define
-
-[ 4 4 tag-mask get ANDI. ] pic-tag jit-define
-
-[
-    3 4 MR
-    4 4 tag-mask get ANDI.
-    0 4 tuple type-number jit-compare-cell-imm
-    [ 0 swap BNE ]
-    [ 4 tuple-class-offset LI 4 3 4 jit-load-cell-x ]
-    jit-conditional*
-] pic-tuple jit-define
-
-[
-    0 4 0 jit-compare-cell-imm rc-absolute-ppc-2 rt-untagged jit-rel
-] pic-check-tag jit-define
-
-[
-    5 jit-load-literal-arg
-    0 4 5 jit-compare-cell
-] pic-check-tuple jit-define
-
-[
-    [ 0 swap BNE ] [ 0 B rc-relative-ppc-3-pc rt-entry-point jit-rel ] jit-conditional*
-] pic-hit jit-define
-
-! Inline cache miss entry points
-: jit-load-return-address ( -- ) 6 MFLR ;
-
-! These are always in tail position with an existing stack
-! frame, and the stack. The frame setup takes this into account.
-: jit-inline-cache-miss ( -- )
-    jit-save-context
-    3 6 MR
-    4 vm-reg MR
-    ctx-reg 6 MR
-    "inline_cache_miss" jit-call
-    6 ctx-reg MR
-    jit-load-context
-    jit-restore-context ;
-
-[ jit-load-return-address jit-inline-cache-miss ]
-[ 3 MTLR BLRL ]
-[ 3 MTCTR BCTR ]
-\ inline-cache-miss define-combinator-primitive
-
-[ jit-inline-cache-miss ]
-[ 3 MTLR BLRL ]
-[ 3 MTCTR BCTR ]
-\ inline-cache-miss-tail define-combinator-primitive
-
-! ! ! Megamorphic caches
-
-[
-    ! class = ...
-    3 4 MR
-    4 4 tag-mask get ANDI. ! Mask and...
-    4 4 tag-bits get jit-shift-left-logical-imm ! shift tag bits to fixnum
-    0 4 tuple type-number tag-fixnum jit-compare-cell-imm
-    [ 0 swap BNE ]
-    [ 4 tuple-class-offset LI 4 3 4 jit-load-cell-x ]
-    jit-conditional*
-    ! cache = ...
-    3 jit-load-literal-arg
-    ! key = hashcode(class)
-    5 4 jit-class-hashcode
-    ! key &= cache.length - 1
-    5 5 mega-cache-size get 1 - 4 * ANDI.
-    ! cache += array-start-offset
-    3 3 array-start-offset ADDI
-    ! cache += key
-    3 3 5 ADD
-    ! if(get(cache) == class)
-    6 3 0 jit-load-cell
-    0 6 4 jit-compare-cell
-    [ 0 swap BNE ]
-    [
-        ! megamorphic_cache_hits++
-        4 jit-load-megamorphic-cache-arg
-        5 4 0 jit-load-cell
-        5 5 1 ADDI
-        5 4 0 jit-save-cell
-        ! ... goto get(cache + cell-size)
-        5 word-entry-point-offset LI
-        3 3 cell-size jit-load-cell
-        3 3 5 jit-load-cell-x
-        3 MTCTR
-        BCTR
-    ]
-    jit-conditional*
-    ! fall-through on miss
-] mega-lookup jit-define
-
-! ! ! Sub-primitives
-
-! Quotations and words
-[
-    3 ds-reg 0 jit-load-cell
-    ds-reg dup cell-size SUBI
-]
-[ jit-call-quot ]
-[ jit-jump-quot ] \ (call) define-combinator-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    ds-reg dup cell-size SUBI
-    4 word-entry-point-offset LI
-    4 3 4 jit-load-cell-x
-]
-[ 4 MTLR BLRL ]
-[ 4 MTCTR BCTR ] \ (execute) define-combinator-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    ds-reg dup cell-size SUBI
-    4 word-entry-point-offset LI
-    4 3 4 jit-load-cell-x
-    4 MTCTR BCTR
-] jit-execute jit-define
-
-! Special primitives
-[
-    frame-reg 3 MR
-
-    3 vm-reg MR
-    "begin_callback" jit-call
-
-    jit-load-context
-    jit-restore-context
-
-    ! Call quotation
-    3 frame-reg MR
-    jit-call-quot
-
-    jit-save-context
-
-    3 vm-reg MR
-    "end_callback" jit-call
-] \ c-to-factor define-sub-primitive
-
-[
-    ! Unwind stack frames
-    1 4 MR
-
-    ! Load VM pointer into vm-reg, since we're entering from
-    ! C code
-    vm-reg jit-load-vm
-
-    ! Load ds and rs registers
-    jit-load-context
-    jit-restore-context
-
-    ! We have changed the stack; load return address again
-    0 1 lr-save jit-load-cell
-    0 MTLR
-
-    ! Call quotation
-    jit-jump-quot
-] \ unwind-native-frames define-sub-primitive
-
-[
-    7 0 LI
-    7 1 lr-save jit-save-cell
-
-    ! Load callstack object
-    6 ds-reg 0 jit-load-cell
-    ds-reg ds-reg cell-size SUBI
-    ! Get ctx->callstack_bottom
-    jit-load-context
-    3 ctx-reg context-callstack-bottom-offset jit-load-cell
-    ! Get top of callstack object -- 'src' for memcpy
-    4 6 callstack-top-offset ADDI
-    ! Get callstack length, in bytes --- 'len' for memcpy
-    7 callstack-length-offset LI
-    5 6 7 jit-load-cell-x
-    5 5 jit-shift-tag-bits
-    ! Compute new stack pointer -- 'dst' for memcpy
-    3 3 5 SUB
-    ! Install new stack pointer
-    1 3 MR
-    ! Call memcpy; arguments are now in the correct registers
-    1 1 -16 cell-size * jit-save-cell-update
-    "factor_memcpy" jit-call
-    1 1 0 jit-load-cell
-    ! Return with new callstack
-    0 1 lr-save jit-load-cell
-    0 MTLR
-    BLR
-] \ set-callstack define-sub-primitive
-
-[
-    jit-save-context
-    4 vm-reg MR
-    "lazy_jit_compile" jit-call
-]
-[ jit-call-quot ]
-[ jit-jump-quot ]
-\ lazy-jit-compile define-combinator-primitive
-
-! Objects
-[
-    3 ds-reg 0 jit-load-cell
-    3 3 tag-mask get ANDI.
-    3 3 tag-bits get jit-shift-left-logical-imm
-    3 ds-reg 0 jit-save-cell
-] \ tag define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell   ! Load m
-    4 ds-reg cell-size neg jit-load-cell-update ! Load obj
-    3 3 jit-shift-fixnum-slot  ! Shift to a cell-size multiple
-    4 4 jit-mask-tag-bits      ! Clear tag bits on obj
-    3 4 3 jit-load-cell-x      ! Load cell at &obj[m]
-    3 ds-reg 0 jit-save-cell   ! Push the result to the stack
-] \ slot define-sub-primitive
-
-[
-    ! load string index from stack
-    3 ds-reg cell-size neg jit-load-cell
-    3 3 jit-shift-tag-bits
-    ! load string from stack
-    4 ds-reg 0 jit-load-cell
-    ! load character
-    4 4 string-offset ADDI
-    3 3 4 LBZX
-    3 3 tag-bits get jit-shift-left-logical-imm
-    ! store character to stack
-    ds-reg ds-reg cell-size SUBI
-    3 ds-reg 0 jit-save-cell
-] \ string-nth-fast define-sub-primitive
-
-! Shufflers
-[
-    ds-reg dup cell-size SUBI
-] \ drop define-sub-primitive
-
-[
-    ds-reg dup 2 cell-size * SUBI
-] \ 2drop define-sub-primitive
-
-[
-    ds-reg dup 3 cell-size * SUBI
-] \ 3drop define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    3 ds-reg cell-size jit-save-cell-update
-] \ dup define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    4 ds-reg cell-size neg jit-load-cell
-    ds-reg dup 2 cell-size * ADDI
-    3 ds-reg 0 jit-save-cell
-    4 ds-reg cell-size neg jit-save-cell
-] \ 2dup define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    4 ds-reg cell-size neg jit-load-cell
-    5 ds-reg cell-size neg 2 * jit-load-cell
-    ds-reg dup cell-size 3 * ADDI
-    3 ds-reg 0 jit-save-cell
-    4 ds-reg cell-size neg jit-save-cell
-    5 ds-reg cell-size neg 2 * jit-save-cell
-] \ 3dup define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    ds-reg dup cell-size SUBI
-    3 ds-reg 0 jit-save-cell
-] \ nip define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    ds-reg dup cell-size 2 * SUBI
-    3 ds-reg 0 jit-save-cell
-] \ 2nip define-sub-primitive
-
-[
-    3 ds-reg cell-size neg jit-load-cell
-    3 ds-reg cell-size jit-save-cell-update
-] \ over define-sub-primitive
-
-[
-    3 ds-reg cell-size neg 2 * jit-load-cell
-    3 ds-reg cell-size jit-save-cell-update
-] \ pick define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    4 ds-reg cell-size neg jit-load-cell
-    4 ds-reg 0 jit-save-cell
-    3 ds-reg cell-size jit-save-cell-update
-] \ dupd define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    4 ds-reg cell-size neg jit-load-cell
-    3 ds-reg cell-size neg jit-save-cell
-    4 ds-reg 0 jit-save-cell
-] \ swap define-sub-primitive
-
-[
-    3 ds-reg cell-size neg jit-load-cell
-    4 ds-reg cell-size neg 2 * jit-load-cell
-    3 ds-reg cell-size neg 2 * jit-save-cell
-    4 ds-reg cell-size neg jit-save-cell
-] \ swapd define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    4 ds-reg cell-size neg jit-load-cell
-    5 ds-reg cell-size neg 2 * jit-load-cell
-    4 ds-reg cell-size neg 2 * jit-save-cell
-    3 ds-reg cell-size neg jit-save-cell
-    5 ds-reg 0 jit-save-cell
-] \ rot define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    4 ds-reg cell-size neg jit-load-cell
-    5 ds-reg cell-size neg 2 * jit-load-cell
-    3 ds-reg cell-size neg 2 * jit-save-cell
-    5 ds-reg cell-size neg jit-save-cell
-    4 ds-reg 0 jit-save-cell
-] \ -rot define-sub-primitive
-
-[ jit->r ] \ load-local define-sub-primitive
-
-! Comparisons
-: jit-compare ( insn -- )
-    t jit-literal
-    3 jit-load-literal-arg
-    4 ds-reg 0 jit-load-cell
-    5 ds-reg cell-size neg jit-load-cell-update
-    0 5 4 jit-compare-cell
-    [ 0 8 ] dip execute( cr offset -- )
-    3 \ f type-number LI
-    3 ds-reg 0 jit-save-cell ;
-
-: define-jit-compare ( insn word -- )
-    [ [ jit-compare ] curry ] dip define-sub-primitive ;
-
-\ BEQ \ eq? define-jit-compare
-\ BGE \ fixnum>= define-jit-compare
-\ BLE \ fixnum<= define-jit-compare
-\ BGT \ fixnum> define-jit-compare
-\ BLT \ fixnum< define-jit-compare
-
-! Math
-[
-    3 ds-reg 0 jit-load-cell
-    ds-reg ds-reg cell-size SUBI
-    4 ds-reg 0 jit-load-cell
-    3 3 4 OR
-    3 3 tag-mask get ANDI.
-    4 \ f type-number LI
-    0 3 0 jit-compare-cell-imm
-    [ 0 swap BNE ] [ 4 1 tag-fixnum LI ] jit-conditional*
-    4 ds-reg 0 jit-save-cell
-] \ both-fixnums? define-sub-primitive
-
-: jit-math ( insn -- )
-    3 ds-reg 0 jit-load-cell
-    4 ds-reg cell-size neg jit-load-cell-update
-    [ 5 3 4 ] dip execute( dst src1 src2 -- )
-    5 ds-reg 0 jit-save-cell ;
-
-[ \ ADD jit-math ] \ fixnum+fast define-sub-primitive
-
-[ \ SUBF jit-math ] \ fixnum-fast define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    4 ds-reg cell-size neg jit-load-cell-update
-    4 4 jit-shift-tag-bits
-    5 3 4 jit-multiply-low
-    5 ds-reg 0 jit-save-cell
-] \ fixnum*fast define-sub-primitive
-
-[ \ AND jit-math ] \ fixnum-bitand define-sub-primitive
-
-[ \ OR jit-math ] \ fixnum-bitor define-sub-primitive
-
-[ \ XOR jit-math ] \ fixnum-bitxor define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    3 3 NOT
-    3 3 tag-mask get XORI
-    3 ds-reg 0 jit-save-cell
-] \ fixnum-bitnot define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell ! Load amount to shift
-    3 3 jit-shift-tag-bits   ! Shift out tag bits
-    ds-reg ds-reg cell-size SUBI
-    4 ds-reg 0 jit-load-cell ! Load value to shift
-    5 4 3 jit-shift-left-logical    ! Shift left
-    6 3 NEG                         ! Negate shift amount
-    7 4 6 jit-shift-right-algebraic ! Shift right
-    7 7 jit-mask-tag-bits           ! Mask out tag bits
-    0 3 0 jit-compare-cell-imm
-    [ 0 swap BGT ] [ 5 7 MR ] jit-conditional*
-    5 ds-reg 0 jit-save-cell
-] \ fixnum-shift-fast define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    ds-reg ds-reg cell-size SUBI
-    4 ds-reg 0 jit-load-cell
-    5 4 3 jit-divide
-    6 5 3 jit-multiply-low
-    7 4 6 SUB
-    7 ds-reg 0 jit-save-cell
-] \ fixnum-mod define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    ds-reg ds-reg cell-size SUBI
-    4 ds-reg 0 jit-load-cell
-    5 4 3 jit-divide
-    5 5 tag-bits get jit-shift-left-logical-imm
-    5 ds-reg 0 jit-save-cell
-] \ fixnum/i-fast define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    4 ds-reg cell-size neg jit-load-cell
-    5 4 3 jit-divide
-    6 5 3 jit-multiply-low
-    7 4 6 SUB
-    5 5 tag-bits get jit-shift-left-logical-imm
-    5 ds-reg cell-size neg jit-save-cell
-    7 ds-reg 0 jit-save-cell
-] \ fixnum/mod-fast define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    3 3 jit-shift-fixnum-slot
-    3 rs-reg 3 jit-load-cell-x
-    3 ds-reg 0 jit-save-cell
-] \ get-local define-sub-primitive
-
-[
-    3 ds-reg 0 jit-load-cell
-    ds-reg ds-reg cell-size SUBI
-    3 3 jit-shift-fixnum-slot
-    rs-reg rs-reg 3 SUB
-] \ drop-locals define-sub-primitive
-
-! Overflowing fixnum arithmetic
-:: jit-overflow ( insn func -- )
-    ds-reg ds-reg cell-size SUBI
-    jit-save-context
-    3 ds-reg 0 jit-load-cell
-    4 ds-reg cell-size jit-load-cell
-    0 0 LI
-    0 MTXER
-    6 4 3 insn call( d a s -- )
-    6 ds-reg 0 jit-save-cell
-    [ 0 swap BNS ]
-    [
-        5 vm-reg MR
-        func jit-call
-    ]
-    jit-conditional* ;
-
-[ [ ADDO. ] "overflow_fixnum_add" jit-overflow ] \ fixnum+ define-sub-primitive
-
-[ [ SUBFO. ] "overflow_fixnum_subtract" jit-overflow ] \ fixnum- define-sub-primitive
-
-[
-    ds-reg ds-reg cell-size SUBI
-    jit-save-context
-    3 ds-reg 0 jit-load-cell
-    3 3 jit-shift-tag-bits
-    4 ds-reg cell-size jit-load-cell
-    0 0 LI
-    0 MTXER
-    6 3 4 jit-multiply-low-ov-rc
-    6 ds-reg 0 jit-save-cell
-    [ 0 swap BNS ]
-    [
-        4 4 jit-shift-tag-bits
-        5 vm-reg MR
-        "overflow_fixnum_multiply" jit-call
-    ]
-    jit-conditional*
-] \ fixnum* define-sub-primitive
-
-! Contexts
-:: jit-switch-context ( reg -- )
-    7 0 LI
-    7 1 lr-save jit-save-cell
-
-    ! Make the new context the current one
-    ctx-reg reg MR
-    ctx-reg vm-reg vm-context-offset jit-save-cell
-
-    ! Load new stack pointer
-    1 ctx-reg context-callstack-top-offset jit-load-cell
-
-    ! Load new ds, rs registers
-    jit-restore-context ;
-
-: jit-pop-context-and-param ( -- )
-    3 ds-reg 0 jit-load-cell
-    4 alien-offset LI
-    3 3 4 jit-load-cell-x
-    4 ds-reg cell-size neg jit-load-cell
-    ds-reg ds-reg cell-size 2 * SUBI ;
-
-: jit-push-param ( -- )
-    ds-reg ds-reg cell-size ADDI
-    4 ds-reg 0 jit-save-cell ;
-
-: jit-set-context ( -- )
-    jit-pop-context-and-param
-    jit-save-context
-    3 jit-switch-context
-    jit-push-param ;
-
-[ jit-set-context ] \ (set-context) define-sub-primitive
-
-: jit-pop-quot-and-param ( -- )
-    3 ds-reg 0 jit-load-cell
-    4 ds-reg cell-size neg jit-load-cell
-    ds-reg ds-reg cell-size 2 * SUBI ;
-
-: jit-start-context ( -- )
-    ! Create the new context in return-reg. Have to save context
-    ! twice, first before calling new_context() which may GC,
-    ! and again after popping the two parameters from the stack.
-    jit-save-context
-    3 vm-reg MR
-    "new_context" jit-call
-
-    6 3 MR
-    jit-pop-quot-and-param
-    jit-save-context
-    6 jit-switch-context
-    jit-push-param
-    jit-jump-quot ;
-
-[ jit-start-context ] \ (start-context) define-sub-primitive
-
-: jit-delete-current-context ( -- )
-    jit-load-context
-    3 vm-reg MR
-    4 ctx-reg MR
-    "delete_context" jit-call ;
-
-[
-    jit-delete-current-context
-    jit-set-context
-] \ (set-context-and-delete) define-sub-primitive
-
-: jit-start-context-and-delete ( -- )
-    jit-load-context
-    3 vm-reg MR
-    4 ctx-reg MR
-    "reset_context" jit-call
-    jit-pop-quot-and-param
-    ctx-reg jit-switch-context
-    jit-push-param
-    jit-jump-quot ;
-
-[
-    jit-start-context-and-delete
-] \ (start-context-and-delete) define-sub-primitive
-
-[ "bootstrap.ppc" forget-vocab ] with-compilation-unit
diff --git a/basis/cpu/x86/32/bootstrap.factor b/basis/cpu/x86/32/bootstrap.factor
deleted file mode 100755 (executable)
index b601c86..0000000
+++ /dev/null
@@ -1,371 +0,0 @@
-! Copyright (C) 2007, 2011 Slava Pestov.
-! See http://factorcode.org/license.txt for BSD license.
-USING: bootstrap.image.private kernel kernel.private namespaces
-system cpu.x86.assembler cpu.x86.assembler.operands layouts
-vocabs parser compiler.constants compiler.codegen.relocation
-sequences math math.private generic.single.private
-threads.private locals ;
-IN: bootstrap.x86
-
-4 \ cell set
-
-: leaf-stack-frame-size ( -- n ) 4 bootstrap-cells ;
-: signal-handler-stack-frame-size ( -- n ) 12 bootstrap-cells ;
-: stack-frame-size ( -- n ) 8 bootstrap-cells ;
-: shift-arg ( -- reg ) ECX ;
-: div-arg ( -- reg ) EAX ;
-: mod-arg ( -- reg ) EDX ;
-: temp0 ( -- reg ) EAX ;
-: temp1 ( -- reg ) ECX ;
-: temp2 ( -- reg ) EBX ;
-: temp3 ( -- reg ) EDX ;
-: pic-tail-reg ( -- reg ) EDX ;
-: stack-reg ( -- reg ) ESP ;
-: frame-reg ( -- reg ) EBP ;
-: vm-reg ( -- reg ) EBX ;
-: ctx-reg ( -- reg ) EBP ;
-: nv-regs ( -- seq ) { ESI EDI EBX } ;
-: volatile-regs ( -- seq ) { EAX ECX EDX } ;
-: nv-reg ( -- reg ) ESI ;
-: ds-reg ( -- reg ) ESI ;
-: rs-reg ( -- reg ) EDI ;
-: link-reg ( -- reg ) EBX ;
-: fixnum>slot@ ( -- ) temp0 2 SAR ;
-: rex-length ( -- n ) 0 ;
-: red-zone-size ( -- n ) 0 ;
-
-: jit-call ( name -- )
-    0 CALL f rc-relative rel-dlsym ;
-
-[
-    pic-tail-reg 0 MOV 0 rc-absolute-cell rel-here
-    0 JMP f rc-relative rel-word-pic-tail
-] jit-word-jump jit-define
-
-: jit-load-vm ( -- )
-    vm-reg 0 MOV 0 rc-absolute-cell rel-vm ;
-
-: jit-load-context ( -- )
-    ! VM pointer must be in vm-reg already
-    ctx-reg vm-reg vm-context-offset [+] MOV ;
-
-: jit-save-context ( -- )
-    jit-load-context
-    ECX ESP -4 [+] LEA
-    ctx-reg context-callstack-top-offset [+] ECX MOV
-    ctx-reg context-datastack-offset [+] ds-reg MOV
-    ctx-reg context-retainstack-offset [+] rs-reg MOV ;
-
-: jit-restore-context ( -- )
-    ds-reg ctx-reg context-datastack-offset [+] MOV
-    rs-reg ctx-reg context-retainstack-offset [+] MOV ;
-
-[
-    ! ctx-reg is preserved across the call because it is
-    ! non-volatile in the C ABI
-    jit-load-vm
-    jit-save-context
-    ! call the primitive
-    ESP [] vm-reg MOV
-    0 CALL f f rc-relative rel-dlsym
-    jit-restore-context
-] jit-primitive jit-define
-
-: jit-jump-quot ( -- )
-    EAX quot-entry-point-offset [+] JMP ;
-
-: jit-call-quot ( -- )
-    EAX quot-entry-point-offset [+] CALL ;
-
-[
-    jit-load-vm
-    ESP [] vm-reg MOV
-    EAX EBP 8 [+] MOV
-    ESP 4 [+] EAX MOV
-    "begin_callback" jit-call
-
-    jit-call-quot
-
-    jit-load-vm
-    ESP [] vm-reg MOV
-    "end_callback" jit-call
-] \ c-to-factor define-sub-primitive
-
-: signal-handler-save-regs ( -- regs )
-    { EAX ECX EDX EBX EBP ESI EDI } ;
-
-[
-    EAX ds-reg [] MOV
-    ds-reg bootstrap-cell SUB
-]
-[ jit-call-quot ]
-[ jit-jump-quot ]
-\ (call) define-combinator-primitive
-
-! unwind-native-frames is marked as "special" in vm/quotations.cpp
-! so it does not have a standard prolog
-[
-    ! Load ds and rs registers
-    jit-load-vm
-    jit-load-context
-    jit-restore-context
-
-    ! clear the fault flag
-    vm-reg vm-fault-flag-offset [+] 0 MOV
-
-    ! Windows-specific setup
-    ctx-reg jit-update-seh
-
-    ! Load arguments
-    EAX ESP bootstrap-cell [+] MOV
-    EDX ESP 2 bootstrap-cells [+] MOV
-
-    ! Unwind stack frames
-    ESP EDX MOV
-
-    jit-jump-quot
-] \ unwind-native-frames define-sub-primitive
-
-[
-    ESP 2 SUB
-    ESP [] FNSTCW
-    FNINIT
-    AX ESP [] MOV
-    ESP 2 ADD
-] \ fpu-state define-sub-primitive
-
-[
-    ESP stack-frame-size [+] FLDCW
-] \ set-fpu-state define-sub-primitive
-
-[
-    ! Load callstack object
-    temp3 ds-reg [] MOV
-    ds-reg bootstrap-cell SUB
-    ! Get ctx->callstack_bottom
-    jit-load-vm
-    jit-load-context
-    temp0 ctx-reg context-callstack-bottom-offset [+] MOV
-    ! Get top of callstack object -- 'src' for memcpy
-    temp1 temp3 callstack-top-offset [+] LEA
-    ! Get callstack length, in bytes --- 'len' for memcpy
-    temp2 temp3 callstack-length-offset [+] MOV
-    temp2 tag-bits get SHR
-    ! Compute new stack pointer -- 'dst' for memcpy
-    temp0 temp2 SUB
-    ! Install new stack pointer
-    ESP temp0 MOV
-    ! Call memcpy
-    temp2 PUSH
-    temp1 PUSH
-    temp0 PUSH
-    "factor_memcpy" jit-call
-    ESP 12 ADD
-    ! Return with new callstack
-    0 RET
-] \ set-callstack define-sub-primitive
-
-[
-    jit-load-vm
-    jit-save-context
-
-    ! Store arguments
-    ESP [] EAX MOV
-    ESP 4 [+] vm-reg MOV
-
-    ! Call VM
-    "lazy_jit_compile" jit-call
-]
-[ jit-call-quot ]
-[ jit-jump-quot ]
-\ lazy-jit-compile define-combinator-primitive
-
-[
-    temp1 0xffffffff CMP f rc-absolute-cell rel-literal
-] pic-check-tuple jit-define
-
-! Inline cache miss entry points
-: jit-load-return-address ( -- )
-    pic-tail-reg ESP stack-frame-size bootstrap-cell - [+] MOV ;
-
-! These are always in tail position with an existing stack
-! frame, and the stack. The frame setup takes this into account.
-: jit-inline-cache-miss ( -- )
-    jit-load-vm
-    jit-save-context
-    ESP 4 [+] vm-reg MOV
-    ESP [] pic-tail-reg MOV
-    0 CALL rc-relative rel-inline-cache-miss
-    jit-restore-context ;
-
-[ jit-load-return-address jit-inline-cache-miss ]
-[ EAX CALL ]
-[ EAX JMP ]
-\ inline-cache-miss define-combinator-primitive
-
-[ jit-inline-cache-miss ]
-[ EAX CALL ]
-[ EAX JMP ]
-\ inline-cache-miss-tail define-combinator-primitive
-
-! Overflowing fixnum arithmetic
-: jit-overflow ( insn func -- )
-    ds-reg 4 SUB
-    jit-load-vm
-    jit-save-context
-    EAX ds-reg [] MOV
-    EDX ds-reg 4 [+] MOV
-    EBX EAX MOV
-    [ [ EBX EDX ] dip call( dst src -- ) ] dip
-    ds-reg [] EBX MOV
-    [ JNO ]
-    [
-        ESP [] EAX MOV
-        ESP 4 [+] EDX MOV
-        jit-load-vm
-        ESP 8 [+] vm-reg MOV
-        jit-call
-    ]
-    jit-conditional ;
-
-[ [ ADD ] "overflow_fixnum_add" jit-overflow ] \ fixnum+ define-sub-primitive
-
-[ [ SUB ] "overflow_fixnum_subtract" jit-overflow ] \ fixnum- define-sub-primitive
-
-[
-    ds-reg 4 SUB
-    jit-load-vm
-    jit-save-context
-    EBX ds-reg [] MOV
-    EAX EBX MOV
-    EBP ds-reg 4 [+] MOV
-    EBP tag-bits get SAR
-    EBP IMUL
-    ds-reg [] EAX MOV
-    [ JNO ]
-    [
-        EBX tag-bits get SAR
-        ESP [] EBX MOV
-        ESP 4 [+] EBP MOV
-        jit-load-vm
-        ESP 8 [+] vm-reg MOV
-        "overflow_fixnum_multiply" jit-call
-    ]
-    jit-conditional
-] \ fixnum* define-sub-primitive
-
-! Contexts
-: jit-switch-context ( reg -- )
-    ! Push a bogus return address so the GC can track this frame back
-    ! to the owner
-    0 CALL
-
-    ! Make the new context the current one
-    ctx-reg swap MOV
-    vm-reg vm-context-offset [+] ctx-reg MOV
-
-    ! Load new stack pointer
-    ESP ctx-reg context-callstack-top-offset [+] MOV
-
-    ! Windows-specific setup
-    ctx-reg jit-update-tib
-
-    ! Load new ds, rs registers
-    jit-restore-context ;
-
-: jit-set-context ( -- )
-    ! Load context and parameter from datastack
-    EAX ds-reg [] MOV
-    EAX EAX alien-offset [+] MOV
-    EDX ds-reg -4 [+] MOV
-    ds-reg 8 SUB
-
-    ! Save ds, rs registers
-    jit-load-vm
-    jit-save-context
-
-    ! Make the new context active
-    EAX jit-switch-context
-
-    ! Windows-specific setup
-    ctx-reg jit-update-seh
-
-    ! Twiddle stack for return
-    ESP 4 ADD
-
-    ! Store parameter to datastack
-    ds-reg 4 ADD
-    ds-reg [] EDX MOV ;
-
-[ jit-set-context ] \ (set-context) define-sub-primitive
-
-: jit-save-quot-and-param ( -- )
-    EDX ds-reg MOV
-    ds-reg 8 SUB ;
-
-: jit-push-param ( -- )
-    EAX EDX -4 [+] MOV
-    ds-reg 4 ADD
-    ds-reg [] EAX MOV ;
-
-: jit-start-context ( -- )
-    ! Create the new context in return-reg
-    jit-load-vm
-    jit-save-context
-    ESP [] vm-reg MOV
-    "new_context" jit-call
-
-    jit-save-quot-and-param
-
-    ! Make the new context active
-    jit-load-vm
-    jit-save-context
-    EAX jit-switch-context
-
-    jit-push-param
-
-    ! Windows-specific setup
-    jit-install-seh
-
-    ! Push a fake return address
-    0 PUSH
-
-    ! Jump to initial quotation
-    EAX EDX [] MOV
-    jit-jump-quot ;
-
-[ jit-start-context ] \ (start-context) define-sub-primitive
-
-: jit-delete-current-context ( -- )
-    jit-load-vm
-    jit-load-context
-    ESP [] vm-reg MOV
-    ESP 4 [+] ctx-reg MOV
-    "delete_context" jit-call ;
-
-[
-    jit-delete-current-context
-    jit-set-context
-] \ (set-context-and-delete) define-sub-primitive
-
-: jit-start-context-and-delete ( -- )
-    jit-load-vm
-    jit-load-context
-    ESP [] vm-reg MOV
-    ESP 4 [+] ctx-reg MOV
-    "reset_context" jit-call
-
-    jit-save-quot-and-param
-    ctx-reg jit-switch-context
-    jit-push-param
-
-    EAX EDX [] MOV
-    jit-jump-quot ;
-
-[
-    0 EAX MOVABS rc-absolute rel-safepoint
-] \ jit-safepoint jit-define
-
-[
-    jit-start-context-and-delete
-] \ (start-context-and-delete) define-sub-primitive
diff --git a/basis/cpu/x86/32/unix/bootstrap.factor b/basis/cpu/x86/32/unix/bootstrap.factor
deleted file mode 100644 (file)
index 56d1851..0000000
+++ /dev/null
@@ -1,8 +0,0 @@
-! Copyright (C) 2010 Slava Pestov.
-! See http://factorcode.org/license.txt for BSD license.
-USING: kernel parser sequences ;
-IN: bootstrap.x86
-
-<< "vocab:cpu/x86/unix/bootstrap.factor" parse-file suffix! >> call
-<< "vocab:cpu/x86/32/bootstrap.factor" parse-file suffix! >> call
-<< "vocab:cpu/x86/bootstrap.factor" parse-file suffix! >> call
diff --git a/basis/cpu/x86/32/windows/bootstrap.factor b/basis/cpu/x86/32/windows/bootstrap.factor
deleted file mode 100644 (file)
index 801818e..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-! Copyright (C) 2010 Slava Pestov.
-! See http://factorcode.org/license.txt for BSD license.
-USING: bootstrap.image.private compiler.constants
-compiler.codegen.relocation cpu.x86.assembler
-cpu.x86.assembler.operands kernel layouts locals parser
-sequences ;
-IN: bootstrap.x86
-
-: tib-segment ( -- ) FS ;
-: tib-temp ( -- reg ) EAX ;
-
-<< "vocab:cpu/x86/windows/bootstrap.factor" parse-file suffix! >> call
-
-: jit-install-seh ( -- )
-    ! Create a new exception record and store it in the TIB.
-    ! Clobbers tib-temp.
-    ! Align stack
-    ESP 3 bootstrap-cells ADD
-    ! Exception handler address filled in by callback.cpp
-    tib-temp 0 MOV rc-absolute-cell rel-exception-handler
-    tib-temp PUSH
-    ! No next handler
-    0 PUSH
-    ! This is the new exception handler
-    tib-exception-list-offset [] ESP tib-segment MOV ;
-
-:: jit-update-seh ( ctx-reg -- )
-    ! Load exception record structure that jit-install-seh
-    ! created from the bottom of the callstack.
-    ! Clobbers tib-temp.
-    tib-temp ctx-reg context-callstack-bottom-offset [+] MOV
-    tib-temp bootstrap-cell ADD
-    ! Store exception record in TIB.
-    tib-exception-list-offset [] tib-temp tib-segment MOV ;
-
-<< "vocab:cpu/x86/32/bootstrap.factor" parse-file suffix! >> call
-<< "vocab:cpu/x86/bootstrap.factor" parse-file suffix! >> call
diff --git a/basis/cpu/x86/64/bootstrap.factor b/basis/cpu/x86/64/bootstrap.factor
deleted file mode 100755 (executable)
index be447eb..0000000
+++ /dev/null
@@ -1,322 +0,0 @@
-! Copyright (C) 2007, 2011 Slava Pestov.
-! See http://factorcode.org/license.txt for BSD license.
-USING: bootstrap.image.private kernel kernel.private namespaces
-system layouts vocabs parser compiler.constants
-compiler.codegen.relocation math math.private cpu.x86.assembler
-cpu.x86.assembler.operands sequences generic.single.private
-threads.private locals ;
-IN: bootstrap.x86
-
-8 \ cell set
-
-: shift-arg ( -- reg ) RCX ;
-: div-arg ( -- reg ) RAX ;
-: mod-arg ( -- reg ) RDX ;
-: temp0 ( -- reg ) RAX ;
-: temp1 ( -- reg ) RCX ;
-: temp2 ( -- reg ) RDX ;
-: temp3 ( -- reg ) RBX ;
-: pic-tail-reg ( -- reg ) RBX ;
-: return-reg ( -- reg ) RAX ;
-: nv-reg ( -- reg ) RBX ;
-: stack-reg ( -- reg ) RSP ;
-: frame-reg ( -- reg ) RBP ;
-: link-reg ( -- reg ) R11 ;
-: ctx-reg ( -- reg ) R12 ;
-: vm-reg ( -- reg ) R13 ;
-: ds-reg ( -- reg ) R14 ;
-: rs-reg ( -- reg ) R15 ;
-: fixnum>slot@ ( -- ) temp0 1 SAR ;
-: rex-length ( -- n ) 1 ;
-
-: jit-call ( name -- )
-    RAX 0 MOV f rc-absolute-cell rel-dlsym
-    RAX CALL ;
-
-[
-    pic-tail-reg 5 [RIP+] LEA
-    0 JMP f rc-relative rel-word-pic-tail
-] jit-word-jump jit-define
-
-: jit-load-vm ( -- )
-    ! no-op on x86-64. in factor contexts vm-reg always contains the
-    ! vm pointer.
-    ;
-
-: jit-load-context ( -- )
-    ctx-reg vm-reg vm-context-offset [+] MOV ;
-
-: jit-save-context ( -- )
-    jit-load-context
-    R11 RSP -8 [+] LEA
-    ctx-reg context-callstack-top-offset [+] R11 MOV
-    ctx-reg context-datastack-offset [+] ds-reg MOV
-    ctx-reg context-retainstack-offset [+] rs-reg MOV ;
-
-: jit-restore-context ( -- )
-    ds-reg ctx-reg context-datastack-offset [+] MOV
-    rs-reg ctx-reg context-retainstack-offset [+] MOV ;
-
-[
-    ! ctx-reg is preserved across the call because it is non-volatile
-    ! in the C ABI
-    jit-save-context
-    ! call the primitive
-    arg1 vm-reg MOV
-    RAX 0 MOV f f rc-absolute-cell rel-dlsym
-    RAX CALL
-    jit-restore-context
-] jit-primitive jit-define
-
-: jit-jump-quot ( -- ) arg1 quot-entry-point-offset [+] JMP ;
-
-: jit-call-quot ( -- ) arg1 quot-entry-point-offset [+] CALL ;
-
-[
-    arg2 arg1 MOV
-    arg1 vm-reg MOV
-    "begin_callback" jit-call
-
-    ! call the quotation
-    arg1 return-reg MOV
-    jit-call-quot
-
-    arg1 vm-reg MOV
-    "end_callback" jit-call
-] \ c-to-factor define-sub-primitive
-
-: signal-handler-save-regs ( -- regs )
-    { RAX RCX RDX RBX RBP RSI RDI R8 R9 R10 R11 R12 R13 R14 R15 } ;
-
-[
-    arg1 ds-reg [] MOV
-    ds-reg bootstrap-cell SUB
-]
-[ jit-call-quot ]
-[ jit-jump-quot ]
-\ (call) define-combinator-primitive
-
-[
-    ! Unwind stack frames
-    RSP arg2 MOV
-
-    ! Load VM pointer into vm-reg, since we're entering from
-    ! C code
-    vm-reg 0 MOV 0 rc-absolute-cell rel-vm
-
-    ! Load ds and rs registers
-    jit-load-context
-    jit-restore-context
-
-    ! Clear the fault flag
-    vm-reg vm-fault-flag-offset [+] 0 MOV
-
-    ! Call quotation
-    jit-jump-quot
-] \ unwind-native-frames define-sub-primitive
-
-[
-    RSP 2 SUB
-    RSP [] FNSTCW
-    FNINIT
-    AX RSP [] MOV
-    RSP 2 ADD
-] \ fpu-state define-sub-primitive
-
-[
-    RSP 2 SUB
-    RSP [] arg1 16-bit-version-of MOV
-    RSP [] FLDCW
-    RSP 2 ADD
-] \ set-fpu-state define-sub-primitive
-
-[
-    ! Load callstack object
-    arg4 ds-reg [] MOV
-    ds-reg bootstrap-cell SUB
-    ! Get ctx->callstack_bottom
-    jit-load-context
-    arg1 ctx-reg context-callstack-bottom-offset [+] MOV
-    ! Get top of callstack object -- 'src' for memcpy
-    arg2 arg4 callstack-top-offset [+] LEA
-    ! Get callstack length, in bytes --- 'len' for memcpy
-    arg3 arg4 callstack-length-offset [+] MOV
-    arg3 tag-bits get SHR
-    ! Compute new stack pointer -- 'dst' for memcpy
-    arg1 arg3 SUB
-    ! Install new stack pointer
-    RSP arg1 MOV
-    ! Call memcpy; arguments are now in the correct registers
-    ! Create register shadow area for Win64
-    RSP 32 SUB
-    "factor_memcpy" jit-call
-    ! Tear down register shadow area
-    RSP 32 ADD
-    ! Return with new callstack
-    0 RET
-] \ set-callstack define-sub-primitive
-
-[
-    jit-save-context
-    arg2 vm-reg MOV
-    "lazy_jit_compile" jit-call
-    arg1 return-reg MOV
-]
-[ return-reg quot-entry-point-offset [+] CALL ]
-[ jit-jump-quot ]
-\ lazy-jit-compile define-combinator-primitive
-
-[
-    temp2 0xffffffff MOV f rc-absolute-cell rel-literal
-    temp1 temp2 CMP
-] pic-check-tuple jit-define
-
-! Inline cache miss entry points
-: jit-load-return-address ( -- )
-    RBX RSP stack-frame-size bootstrap-cell - [+] MOV ;
-
-! These are always in tail position with an existing stack
-! frame, and the stack. The frame setup takes this into account.
-: jit-inline-cache-miss ( -- )
-    jit-save-context
-    arg1 RBX MOV
-    arg2 vm-reg MOV
-    RAX 0 MOV rc-absolute-cell rel-inline-cache-miss
-    RAX CALL
-    jit-load-context
-    jit-restore-context ;
-
-[ jit-load-return-address jit-inline-cache-miss ]
-[ RAX CALL ]
-[ RAX JMP ]
-\ inline-cache-miss define-combinator-primitive
-
-[ jit-inline-cache-miss ]
-[ RAX CALL ]
-[ RAX JMP ]
-\ inline-cache-miss-tail define-combinator-primitive
-
-! Overflowing fixnum arithmetic
-: jit-overflow ( insn func -- )
-    ds-reg 8 SUB
-    jit-save-context
-    arg1 ds-reg [] MOV
-    arg2 ds-reg 8 [+] MOV
-    arg3 arg1 MOV
-    [ [ arg3 arg2 ] dip call ] dip
-    ds-reg [] arg3 MOV
-    [ JNO ]
-    [ arg3 vm-reg MOV jit-call ]
-    jit-conditional ; inline
-
-[ [ ADD ] "overflow_fixnum_add" jit-overflow ] \ fixnum+ define-sub-primitive
-
-[ [ SUB ] "overflow_fixnum_subtract" jit-overflow ] \ fixnum- define-sub-primitive
-
-[
-    ds-reg 8 SUB
-    jit-save-context
-    RCX ds-reg [] MOV
-    RBX ds-reg 8 [+] MOV
-    RBX tag-bits get SAR
-    RAX RCX MOV
-    RBX IMUL
-    ds-reg [] RAX MOV
-    [ JNO ]
-    [
-        arg1 RCX MOV
-        arg1 tag-bits get SAR
-        arg2 RBX MOV
-        arg3 vm-reg MOV
-        "overflow_fixnum_multiply" jit-call
-    ]
-    jit-conditional
-] \ fixnum* define-sub-primitive
-
-! Contexts
-: jit-switch-context ( reg -- )
-    ! Push a bogus return address so the GC can track this frame back
-    ! to the owner
-    0 CALL
-
-    ! Make the new context the current one
-    ctx-reg swap MOV
-    vm-reg vm-context-offset [+] ctx-reg MOV
-
-    ! Load new stack pointer
-    RSP ctx-reg context-callstack-top-offset [+] MOV
-
-    ! Load new ds, rs registers
-    jit-restore-context
-
-    ctx-reg jit-update-tib ;
-
-: jit-pop-context-and-param ( -- )
-    arg1 ds-reg [] MOV
-    arg1 arg1 alien-offset [+] MOV
-    arg2 ds-reg -8 [+] MOV
-    ds-reg 16 SUB ;
-
-: jit-push-param ( -- )
-    ds-reg 8 ADD
-    ds-reg [] arg2 MOV ;
-
-: jit-set-context ( -- )
-    jit-pop-context-and-param
-    jit-save-context
-    arg1 jit-switch-context
-    RSP 8 ADD
-    jit-push-param ;
-
-[ jit-set-context ] \ (set-context) define-sub-primitive
-
-: jit-pop-quot-and-param ( -- )
-    arg1 ds-reg [] MOV
-    arg2 ds-reg -8 [+] MOV
-    ds-reg 16 SUB ;
-
-: jit-start-context ( -- )
-    ! Create the new context in return-reg. Have to save context
-    ! twice, first before calling new_context() which may GC,
-    ! and again after popping the two parameters from the stack.
-    jit-save-context
-    arg1 vm-reg MOV
-    "new_context" jit-call
-
-    jit-pop-quot-and-param
-    jit-save-context
-    return-reg jit-switch-context
-    jit-push-param
-    jit-jump-quot ;
-
-[ jit-start-context ] \ (start-context) define-sub-primitive
-
-: jit-delete-current-context ( -- )
-    jit-load-context
-    arg1 vm-reg MOV
-    arg2 ctx-reg MOV
-    "delete_context" jit-call ;
-
-[
-    jit-delete-current-context
-    jit-set-context
-] \ (set-context-and-delete) define-sub-primitive
-
-: jit-start-context-and-delete ( -- )
-    jit-load-context
-    arg1 vm-reg MOV
-    arg2 ctx-reg MOV
-    "reset_context" jit-call
-
-    jit-pop-quot-and-param
-    ctx-reg jit-switch-context
-    jit-push-param
-    jit-jump-quot ;
-
-[
-    0 [RIP+] EAX MOV rc-relative rel-safepoint
-] \ jit-safepoint jit-define
-
-[
-    jit-start-context-and-delete
-] \ (start-context-and-delete) define-sub-primitive
diff --git a/basis/cpu/x86/64/unix/bootstrap.factor b/basis/cpu/x86/64/unix/bootstrap.factor
deleted file mode 100644 (file)
index c4abe96..0000000
+++ /dev/null
@@ -1,21 +0,0 @@
-! Copyright (C) 2008 Slava Pestov.
-! See http://factorcode.org/license.txt for BSD license.
-USING: bootstrap.image.private cpu.x86.assembler
-cpu.x86.assembler.operands kernel layouts namespaces parser
-sequences system vocabs ;
-IN: bootstrap.x86
-
-: leaf-stack-frame-size ( -- n ) 2 bootstrap-cells ;
-: signal-handler-stack-frame-size ( -- n ) 20 bootstrap-cells ;
-: stack-frame-size ( -- n ) 4 bootstrap-cells ;
-: nv-regs ( -- seq ) { RBX R12 R13 R14 R15 } ;
-: volatile-regs ( -- seq ) { RAX RCX RDX RSI RDI R8 R9 R10 R11 } ;
-: arg1 ( -- reg ) RDI ;
-: arg2 ( -- reg ) RSI ;
-: arg3 ( -- reg ) RDX ;
-: arg4 ( -- reg ) RCX ;
-: red-zone-size ( -- n ) 128 ;
-
-<< "vocab:cpu/x86/unix/bootstrap.factor" parse-file suffix! >> call
-<< "vocab:cpu/x86/64/bootstrap.factor" parse-file suffix! >> call
-<< "vocab:cpu/x86/bootstrap.factor" parse-file suffix! >> call
diff --git a/basis/cpu/x86/64/windows/bootstrap.factor b/basis/cpu/x86/64/windows/bootstrap.factor
deleted file mode 100644 (file)
index d622161..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-! Copyright (C) 2008 Slava Pestov.
-! See http://factorcode.org/license.txt for BSD license.
-USING: bootstrap.image.private kernel namespaces system layouts
-vocabs sequences cpu.x86.assembler parser
-cpu.x86.assembler.operands ;
-IN: bootstrap.x86
-
-DEFER: stack-reg
-
-: leaf-stack-frame-size ( -- n ) 2 bootstrap-cells ;
-: signal-handler-stack-frame-size ( -- n ) 24 bootstrap-cells ;
-: stack-frame-size ( -- n ) 8 bootstrap-cells ;
-: nv-regs ( -- seq ) { RBX RSI RDI R12 R13 R14 R15 } ;
-: volatile-regs ( -- seq ) { RAX RCX RDX R8 R9 R10 R11 } ;
-: arg1 ( -- reg ) RCX ;
-: arg2 ( -- reg ) RDX ;
-: arg3 ( -- reg ) R8 ;
-: arg4 ( -- reg ) R9 ;
-
-: tib-segment ( -- ) GS ;
-: tib-temp ( -- reg ) R11 ;
-
-: jit-install-seh ( -- ) stack-reg bootstrap-cell ADD ;
-: jit-update-seh ( ctx-reg -- ) drop ;
-
-: red-zone-size ( -- n ) 0 ;
-
-<< "vocab:cpu/x86/windows/bootstrap.factor" parse-file suffix! >> call
-<< "vocab:cpu/x86/64/bootstrap.factor" parse-file suffix! >> call
-<< "vocab:cpu/x86/bootstrap.factor" parse-file suffix! >> call
diff --git a/basis/cpu/x86/bootstrap.factor b/basis/cpu/x86/bootstrap.factor
deleted file mode 100644 (file)
index bf8d346..0000000
+++ /dev/null
@@ -1,649 +0,0 @@
-! Copyright (C) 2007, 2011 Slava Pestov.
-! See http://factorcode.org/license.txt for BSD license.
-USING: bootstrap.image.private compiler.constants
-compiler.codegen.relocation compiler.units cpu.x86.assembler
-cpu.x86.assembler.operands kernel kernel.private layouts
-locals locals.backend make math math.private namespaces sequences
-slots.private strings.private vocabs ;
-IN: bootstrap.x86
-
-big-endian off
-
-! C to Factor entry point
-[
-    ! Optimizing compiler's side of callback accesses
-    ! arguments that are on the stack via the frame pointer.
-    ! On x86-32 fastcall, and x86-64, some arguments are passed
-    ! in registers, and so the only registers that are safe for
-    ! use here are frame-reg, nv-reg and vm-reg.
-    frame-reg PUSH
-    frame-reg stack-reg MOV
-
-    ! Save all non-volatile registers
-    nv-regs [ PUSH ] each
-
-    jit-save-tib
-
-    ! Load VM into vm-reg
-    vm-reg 0 MOV 0 rc-absolute-cell rel-vm
-
-    ! Save old context
-    nv-reg vm-reg vm-context-offset [+] MOV
-    nv-reg PUSH
-
-    ! Switch over to the spare context
-    nv-reg vm-reg vm-spare-context-offset [+] MOV
-    vm-reg vm-context-offset [+] nv-reg MOV
-
-    ! Save C callstack pointer
-    nv-reg context-callstack-save-offset [+] stack-reg MOV
-
-    ! Load Factor stack pointers
-    stack-reg nv-reg context-callstack-bottom-offset [+] MOV
-    nv-reg jit-update-tib
-    jit-install-seh
-
-    rs-reg nv-reg context-retainstack-offset [+] MOV
-    ds-reg nv-reg context-datastack-offset [+] MOV
-
-    ! Call into Factor code
-    link-reg 0 MOV f rc-absolute-cell rel-word
-    link-reg CALL
-
-    ! Load VM into vm-reg; only needed on x86-32, but doesn't
-    ! hurt on x86-64
-    vm-reg 0 MOV 0 rc-absolute-cell rel-vm
-
-    ! Load C callstack pointer
-    nv-reg vm-reg vm-context-offset [+] MOV
-    stack-reg nv-reg context-callstack-save-offset [+] MOV
-
-    ! Load old context
-    nv-reg POP
-    vm-reg vm-context-offset [+] nv-reg MOV
-
-    ! Restore non-volatile registers
-    jit-restore-tib
-
-    nv-regs <reversed> [ POP ] each
-
-    frame-reg POP
-
-    ! Callbacks which return structs, or use stdcall/fastcall/thiscall,
-    ! need a parameter here.
-
-    ! See the comment for M\ x86.32 stack-cleanup in cpu.x86.32
-    0xffff RET f rc-absolute-2 rel-untagged
-] callback-stub jit-define
-
-[
-    ! load literal
-    temp0 0 MOV f rc-absolute-cell rel-literal
-    ! increment datastack pointer
-    ds-reg bootstrap-cell ADD
-    ! store literal on datastack
-    ds-reg [] temp0 MOV
-] jit-push jit-define
-
-[
-    0 CALL f rc-relative rel-word-pic
-] jit-word-call jit-define
-
-! The *-signal-handler subprimitives are special-cased in vm/quotations.cpp
-! not to trigger generation of a stack frame, so they can
-! peform their own prolog/epilog preserving registers.
-
-: jit-signal-handler-prolog ( -- )
-    ! minus a cell each for flags, return address
-    ! use LEA so we don't dirty flags
-    stack-reg stack-reg signal-handler-stack-frame-size
-    2 bootstrap-cells - neg [+] LEA
-
-    signal-handler-save-regs
-    [| r i | stack-reg i bootstrap-cells [+] r MOV ] each-index
-
-    PUSHF
-
-    jit-load-vm ;
-
-: jit-signal-handler-epilog ( -- )
-    POPF
-
-    signal-handler-save-regs
-    [| r i | r stack-reg i bootstrap-cells [+] MOV ] each-index
-
-    stack-reg stack-reg signal-handler-stack-frame-size
-    2 bootstrap-cells - [+] LEA ;
-
-[| |
-    jit-signal-handler-prolog
-    jit-save-context
-    temp0 vm-reg vm-signal-handler-addr-offset [+] MOV
-    temp0 CALL
-    jit-signal-handler-epilog
-    0 RET
-] \ signal-handler define-sub-primitive
-
-[| |
-    jit-signal-handler-prolog
-    jit-save-context
-    temp0 vm-reg vm-signal-handler-addr-offset [+] MOV
-    temp0 CALL
-    jit-signal-handler-epilog
-    ! Pop the fake leaf frame along with our return address
-    leaf-stack-frame-size bootstrap-cell - RET
-] \ leaf-signal-handler define-sub-primitive
-
-[| |
-    jit-signal-handler-prolog
-    temp0 vm-reg vm-signal-handler-addr-offset [+] MOV
-    temp0 CALL
-    jit-signal-handler-epilog
-    red-zone-size RET
-] \ ffi-signal-handler define-sub-primitive
-
-[| |
-    jit-signal-handler-prolog
-    temp0 vm-reg vm-signal-handler-addr-offset [+] MOV
-    temp0 CALL
-    jit-signal-handler-epilog
-    red-zone-size 16 bootstrap-cell - + RET
-] \ ffi-leaf-signal-handler define-sub-primitive
-
-[
-    ! load boolean
-    temp0 ds-reg [] MOV
-    ! pop boolean
-    ds-reg bootstrap-cell SUB
-    ! compare boolean with f
-    temp0 \ f type-number CMP
-    ! jump to true branch if not equal
-    0 JNE f rc-relative rel-word
-    ! jump to false branch if equal
-    0 JMP f rc-relative rel-word
-] jit-if jit-define
-
-: jit->r ( -- )
-    rs-reg bootstrap-cell ADD
-    temp0 ds-reg [] MOV
-    ds-reg bootstrap-cell SUB
-    rs-reg [] temp0 MOV ;
-
-: jit-2>r ( -- )
-    rs-reg 2 bootstrap-cells ADD
-    temp0 ds-reg [] MOV
-    temp1 ds-reg -1 bootstrap-cells [+] MOV
-    ds-reg 2 bootstrap-cells SUB
-    rs-reg [] temp0 MOV
-    rs-reg -1 bootstrap-cells [+] temp1 MOV ;
-
-: jit-3>r ( -- )
-    rs-reg 3 bootstrap-cells ADD
-    temp0 ds-reg [] MOV
-    temp1 ds-reg -1 bootstrap-cells [+] MOV
-    temp2 ds-reg -2 bootstrap-cells [+] MOV
-    ds-reg 3 bootstrap-cells SUB
-    rs-reg [] temp0 MOV
-    rs-reg -1 bootstrap-cells [+] temp1 MOV
-    rs-reg -2 bootstrap-cells [+] temp2 MOV ;
-
-: jit-r> ( -- )
-    ds-reg bootstrap-cell ADD
-    temp0 rs-reg [] MOV
-    rs-reg bootstrap-cell SUB
-    ds-reg [] temp0 MOV ;
-
-: jit-2r> ( -- )
-    ds-reg 2 bootstrap-cells ADD
-    temp0 rs-reg [] MOV
-    temp1 rs-reg -1 bootstrap-cells [+] MOV
-    rs-reg 2 bootstrap-cells SUB
-    ds-reg [] temp0 MOV
-    ds-reg -1 bootstrap-cells [+] temp1 MOV ;
-
-: jit-3r> ( -- )
-    ds-reg 3 bootstrap-cells ADD
-    temp0 rs-reg [] MOV
-    temp1 rs-reg -1 bootstrap-cells [+] MOV
-    temp2 rs-reg -2 bootstrap-cells [+] MOV
-    rs-reg 3 bootstrap-cells SUB
-    ds-reg [] temp0 MOV
-    ds-reg -1 bootstrap-cells [+] temp1 MOV
-    ds-reg -2 bootstrap-cells [+] temp2 MOV ;
-
-[
-    jit->r
-    0 CALL f rc-relative rel-word
-    jit-r>
-] jit-dip jit-define
-
-[
-    jit-2>r
-    0 CALL f rc-relative rel-word
-    jit-2r>
-] jit-2dip jit-define
-
-[
-    jit-3>r
-    0 CALL f rc-relative rel-word
-    jit-3r>
-] jit-3dip jit-define
-
-[
-    ! load from stack
-    temp0 ds-reg [] MOV
-    ! pop stack
-    ds-reg bootstrap-cell SUB
-]
-[ temp0 word-entry-point-offset [+] CALL ]
-[ temp0 word-entry-point-offset [+] JMP ]
-\ (execute) define-combinator-primitive
-
-[
-    temp0 ds-reg [] MOV
-    ds-reg bootstrap-cell SUB
-    temp0 word-entry-point-offset [+] JMP
-] jit-execute jit-define
-
-[
-    stack-reg stack-frame-size bootstrap-cell - SUB
-] jit-prolog jit-define
-
-[
-    stack-reg stack-frame-size bootstrap-cell - ADD
-] jit-epilog jit-define
-
-[ 0 RET ] jit-return jit-define
-
-! ! ! Polymorphic inline caches
-
-! The PIC stubs are not permitted to touch pic-tail-reg.
-
-! Load a value from a stack position
-[
-    temp1 ds-reg 0x7f [+] MOV f rc-absolute-1 rel-untagged
-] pic-load jit-define
-
-[ temp1 tag-mask get AND ] pic-tag jit-define
-
-[
-    temp0 temp1 MOV
-    temp1 tag-mask get AND
-    temp1 tuple type-number CMP
-    [ JNE ]
-    [ temp1 temp0 tuple-class-offset [+] MOV ]
-    jit-conditional
-] pic-tuple jit-define
-
-[
-    temp1 0x7f CMP f rc-absolute-1 rel-untagged
-] pic-check-tag jit-define
-
-[ 0 JE f rc-relative rel-word ] pic-hit jit-define
-
-! ! ! Megamorphic caches
-
-[
-    ! class = ...
-    temp0 temp1 MOV
-    temp1 tag-mask get AND
-    temp1 tag-bits get SHL
-    temp1 tuple type-number tag-fixnum CMP
-    [ JNE ]
-    [ temp1 temp0 tuple-class-offset [+] MOV ]
-    jit-conditional
-    ! cache = ...
-    temp0 0 MOV f rc-absolute-cell rel-literal
-    ! key = hashcode(class)
-    temp2 temp1 MOV
-    bootstrap-cell 4 = [ temp2 1 SHR ] when
-    ! key &= cache.length - 1
-    temp2 mega-cache-size get 1 - bootstrap-cell * AND
-    ! cache += array-start-offset
-    temp0 array-start-offset ADD
-    ! cache += key
-    temp0 temp2 ADD
-    ! if(get(cache) == class)
-    temp0 [] temp1 CMP
-    [ JNE ]
-    [
-        ! megamorphic_cache_hits++
-        temp1 0 MOV rc-absolute-cell rel-megamorphic-cache-hits
-        temp1 [] 1 ADD
-        ! goto get(cache + bootstrap-cell)
-        temp0 temp0 bootstrap-cell [+] MOV
-        temp0 word-entry-point-offset [+] JMP
-        ! fall-through on miss
-    ] jit-conditional
-] mega-lookup jit-define
-
-! ! ! Sub-primitives
-
-! Objects
-[
-    ! load from stack
-    temp0 ds-reg [] MOV
-    ! compute tag
-    temp0 tag-mask get AND
-    ! tag the tag
-    temp0 tag-bits get SHL
-    ! push to stack
-    ds-reg [] temp0 MOV
-] \ tag define-sub-primitive
-
-[
-    ! load slot number
-    temp0 ds-reg [] MOV
-    ! adjust stack pointer
-    ds-reg bootstrap-cell SUB
-    ! load object
-    temp1 ds-reg [] MOV
-    ! turn slot number into offset
-    fixnum>slot@
-    ! mask off tag
-    temp1 tag-bits get SHR
-    temp1 tag-bits get SHL
-    ! load slot value
-    temp0 temp1 temp0 [+] MOV
-    ! push to stack
-    ds-reg [] temp0 MOV
-] \ slot define-sub-primitive
-
-[
-    ! load string index from stack
-    temp0 ds-reg bootstrap-cell neg [+] MOV
-    temp0 tag-bits get SHR
-    ! load string from stack
-    temp1 ds-reg [] MOV
-    ! load character
-    temp0 8-bit-version-of temp0 temp1 string-offset [++] MOV
-    temp0 temp0 8-bit-version-of MOVZX
-    temp0 tag-bits get SHL
-    ! store character to stack
-    ds-reg bootstrap-cell SUB
-    ds-reg [] temp0 MOV
-] \ string-nth-fast define-sub-primitive
-
-! Shufflers
-[
-    ds-reg bootstrap-cell SUB
-] \ drop define-sub-primitive
-
-[
-    ds-reg 2 bootstrap-cells SUB
-] \ 2drop define-sub-primitive
-
-[
-    ds-reg 3 bootstrap-cells SUB
-] \ 3drop define-sub-primitive
-
-[
-    ds-reg 4 bootstrap-cells SUB
-] \ 4drop define-sub-primitive
-
-[
-    temp0 ds-reg [] MOV
-    ds-reg bootstrap-cell ADD
-    ds-reg [] temp0 MOV
-] \ dup define-sub-primitive
-
-[
-    temp0 ds-reg [] MOV
-    temp1 ds-reg bootstrap-cell neg [+] MOV
-    ds-reg 2 bootstrap-cells ADD
-    ds-reg [] temp0 MOV
-    ds-reg bootstrap-cell neg [+] temp1 MOV
-] \ 2dup define-sub-primitive
-
-[
-    temp0 ds-reg [] MOV
-    temp1 ds-reg -1 bootstrap-cells [+] MOV
-    temp3 ds-reg -2 bootstrap-cells [+] MOV
-    ds-reg 3 bootstrap-cells ADD
-    ds-reg [] temp0 MOV
-    ds-reg -1 bootstrap-cells [+] temp1 MOV
-    ds-reg -2 bootstrap-cells [+] temp3 MOV
-] \ 3dup define-sub-primitive
-
-[
-    temp0 ds-reg [] MOV
-    temp1 ds-reg -1 bootstrap-cells [+] MOV
-    temp2 ds-reg -2 bootstrap-cells [+] MOV
-    temp3 ds-reg -3 bootstrap-cells [+] MOV
-    ds-reg 4 bootstrap-cells ADD
-    ds-reg [] temp0 MOV
-    ds-reg -1 bootstrap-cells [+] temp1 MOV
-    ds-reg -2 bootstrap-cells [+] temp2 MOV
-    ds-reg -3 bootstrap-cells [+] temp3 MOV
-] \ 4dup define-sub-primitive
-
-[
-    temp0 ds-reg [] MOV
-    ds-reg bootstrap-cell SUB
-    ds-reg [] temp0 MOV
-] \ nip define-sub-primitive
-
-[
-    temp0 ds-reg [] MOV
-    ds-reg 2 bootstrap-cells SUB
-    ds-reg [] temp0 MOV
-] \ 2nip define-sub-primitive
-
-[
-    temp0 ds-reg -1 bootstrap-cells [+] MOV
-    ds-reg bootstrap-cell ADD
-    ds-reg [] temp0 MOV
-] \ over define-sub-primitive
-
-[
-    temp0 ds-reg -2 bootstrap-cells [+] MOV
-    ds-reg bootstrap-cell ADD
-    ds-reg [] temp0 MOV
-] \ pick define-sub-primitive
-
-[
-    temp0 ds-reg [] MOV
-    temp1 ds-reg -1 bootstrap-cells [+] MOV
-    ds-reg [] temp1 MOV
-    ds-reg bootstrap-cell ADD
-    ds-reg [] temp0 MOV
-] \ dupd define-sub-primitive
-
-[
-    temp0 ds-reg [] MOV
-    temp1 ds-reg bootstrap-cell neg [+] MOV
-    ds-reg bootstrap-cell neg [+] temp0 MOV
-    ds-reg [] temp1 MOV
-] \ swap define-sub-primitive
-
-[
-    temp0 ds-reg -1 bootstrap-cells [+] MOV
-    temp1 ds-reg -2 bootstrap-cells [+] MOV
-    ds-reg -2 bootstrap-cells [+] temp0 MOV
-    ds-reg -1 bootstrap-cells [+] temp1 MOV
-] \ swapd define-sub-primitive
-
-[
-    temp0 ds-reg [] MOV
-    temp1 ds-reg -1 bootstrap-cells [+] MOV
-    temp3 ds-reg -2 bootstrap-cells [+] MOV
-    ds-reg -2 bootstrap-cells [+] temp1 MOV
-    ds-reg -1 bootstrap-cells [+] temp0 MOV
-    ds-reg [] temp3 MOV
-] \ rot define-sub-primitive
-
-[
-    temp0 ds-reg [] MOV
-    temp1 ds-reg -1 bootstrap-cells [+] MOV
-    temp3 ds-reg -2 bootstrap-cells [+] MOV
-    ds-reg -2 bootstrap-cells [+] temp0 MOV
-    ds-reg -1 bootstrap-cells [+] temp3 MOV
-    ds-reg [] temp1 MOV
-] \ -rot define-sub-primitive
-
-[ jit->r ] \ load-local define-sub-primitive
-
-! Comparisons
-: jit-compare ( insn -- )
-    ! load t
-    temp3 0 MOV t rc-absolute-cell rel-literal
-    ! load f
-    temp1 \ f type-number MOV
-    ! load first value
-    temp0 ds-reg [] MOV
-    ! adjust stack pointer
-    ds-reg bootstrap-cell SUB
-    ! compare with second value
-    ds-reg [] temp0 CMP
-    ! move t if true
-    [ temp1 temp3 ] dip execute( dst src -- )
-    ! store
-    ds-reg [] temp1 MOV ;
-
-: define-jit-compare ( insn word -- )
-    [ [ jit-compare ] curry ] dip define-sub-primitive ;
-
-\ CMOVE \ eq? define-jit-compare
-\ CMOVGE \ fixnum>= define-jit-compare
-\ CMOVLE \ fixnum<= define-jit-compare
-\ CMOVG \ fixnum> define-jit-compare
-\ CMOVL \ fixnum< define-jit-compare
-
-! Math
-: jit-math ( insn -- )
-    ! load second input
-    temp0 ds-reg [] MOV
-    ! pop stack
-    ds-reg bootstrap-cell SUB
-    ! compute result
-    [ ds-reg [] temp0 ] dip execute( dst src -- ) ;
-
-[ \ ADD jit-math ] \ fixnum+fast define-sub-primitive
-
-[ \ SUB jit-math ] \ fixnum-fast define-sub-primitive
-
-[
-    ! load second input
-    temp0 ds-reg [] MOV
-    ! pop stack
-    ds-reg bootstrap-cell SUB
-    ! load first input
-    temp1 ds-reg [] MOV
-    ! untag second input
-    temp0 tag-bits get SAR
-    ! multiply
-    temp0 temp1 IMUL2
-    ! push result
-    ds-reg [] temp0 MOV
-] \ fixnum*fast define-sub-primitive
-
-[ \ AND jit-math ] \ fixnum-bitand define-sub-primitive
-
-[ \ OR jit-math ] \ fixnum-bitor define-sub-primitive
-
-[ \ XOR jit-math ] \ fixnum-bitxor define-sub-primitive
-
-[
-    ! complement
-    ds-reg [] NOT
-    ! clear tag bits
-    ds-reg [] tag-mask get XOR
-] \ fixnum-bitnot define-sub-primitive
-
-[
-    ! load shift count
-    shift-arg ds-reg [] MOV
-    ! untag shift count
-    shift-arg tag-bits get SAR
-    ! adjust stack pointer
-    ds-reg bootstrap-cell SUB
-    ! load value
-    temp3 ds-reg [] MOV
-    ! make a copy
-    temp2 temp3 MOV
-    ! compute positive shift value in temp2
-    temp2 CL SHL
-    shift-arg NEG
-    ! compute negative shift value in temp3
-    temp3 CL SAR
-    temp3 tag-mask get bitnot AND
-    shift-arg 0 CMP
-    ! if shift count was negative, move temp0 to temp2
-    temp2 temp3 CMOVGE
-    ! push to stack
-    ds-reg [] temp2 MOV
-] \ fixnum-shift-fast define-sub-primitive
-
-: jit-fixnum-/mod ( -- )
-    ! load second parameter
-    temp1 ds-reg [] MOV
-    ! load first parameter
-    div-arg ds-reg bootstrap-cell neg [+] MOV
-    ! make a copy
-    mod-arg div-arg MOV
-    ! sign-extend
-    mod-arg bootstrap-cell-bits 1 - SAR
-    ! divide
-    temp1 IDIV ;
-
-[
-    jit-fixnum-/mod
-    ! adjust stack pointer
-    ds-reg bootstrap-cell SUB
-    ! push to stack
-    ds-reg [] mod-arg MOV
-] \ fixnum-mod define-sub-primitive
-
-[
-    jit-fixnum-/mod
-    ! adjust stack pointer
-    ds-reg bootstrap-cell SUB
-    ! tag it
-    div-arg tag-bits get SHL
-    ! push to stack
-    ds-reg [] div-arg MOV
-] \ fixnum/i-fast define-sub-primitive
-
-[
-    jit-fixnum-/mod
-    ! tag it
-    div-arg tag-bits get SHL
-    ! push to stack
-    ds-reg [] mod-arg MOV
-    ds-reg bootstrap-cell neg [+] div-arg MOV
-] \ fixnum/mod-fast define-sub-primitive
-
-[
-    temp0 ds-reg [] MOV
-    ds-reg bootstrap-cell SUB
-    temp0 ds-reg [] OR
-    temp0 tag-mask get TEST
-    temp0 \ f type-number MOV
-    temp1 1 tag-fixnum MOV
-    temp0 temp1 CMOVE
-    ds-reg [] temp0 MOV
-] \ both-fixnums? define-sub-primitive
-
-[
-    ! load local number
-    temp0 ds-reg [] MOV
-    ! turn local number into offset
-    fixnum>slot@
-    ! load local value
-    temp0 rs-reg temp0 [+] MOV
-    ! push to stack
-    ds-reg [] temp0 MOV
-] \ get-local define-sub-primitive
-
-[
-    ! load local count
-    temp0 ds-reg [] MOV
-    ! adjust stack pointer
-    ds-reg bootstrap-cell SUB
-    ! turn local number into offset
-    fixnum>slot@
-    ! decrement retain stack pointer
-    rs-reg temp0 SUB
-] \ drop-locals define-sub-primitive
-
-[ "bootstrap.x86" forget-vocab ] with-compilation-unit
diff --git a/basis/cpu/x86/unix/bootstrap.factor b/basis/cpu/x86/unix/bootstrap.factor
deleted file mode 100644 (file)
index 20dd738..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-! Copyright (C) 2010 Slava Pestov.
-! See http://factorcode.org/license.txt for BSD license.
-USING: cpu.x86.assembler cpu.x86.assembler.operands kernel
-layouts ;
-IN: bootstrap.x86
-
-DEFER: stack-reg
-
-: jit-save-tib ( -- ) ;
-: jit-restore-tib ( -- ) ;
-: jit-update-tib ( ctx-reg -- ) drop ;
-: jit-install-seh ( -- ) stack-reg bootstrap-cell ADD ;
-: jit-update-seh ( ctx-reg -- ) drop ;
diff --git a/basis/cpu/x86/windows/bootstrap.factor b/basis/cpu/x86/windows/bootstrap.factor
deleted file mode 100644 (file)
index b81c1eb..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-! Copyright (C) 2010 Slava Pestov.
-! See http://factorcode.org/license.txt for BSD license.
-USING: bootstrap.image.private compiler.constants
-cpu.x86.assembler cpu.x86.assembler.operands kernel layouts
-locals parser sequences ;
-IN: bootstrap.x86
-
-: tib-exception-list-offset ( -- n ) 0 bootstrap-cells ;
-: tib-stack-base-offset ( -- n ) 1 bootstrap-cells ;
-: tib-stack-limit-offset ( -- n ) 2 bootstrap-cells ;
-
-: jit-save-tib ( -- )
-    tib-exception-list-offset [] tib-segment PUSH
-    tib-stack-base-offset [] tib-segment PUSH
-    tib-stack-limit-offset [] tib-segment PUSH ;
-
-: jit-restore-tib ( -- )
-    tib-stack-limit-offset [] tib-segment POP
-    tib-stack-base-offset [] tib-segment POP
-    tib-exception-list-offset [] tib-segment POP ;
-
-:: jit-update-tib ( ctx-reg -- )
-    ! There's a redundant load here because we're not allowed
-    ! to clobber ctx-reg. Clobbers tib-temp.
-    ! Save callstack base in TIB
-    tib-temp ctx-reg context-callstack-seg-offset [+] MOV
-    tib-temp tib-temp segment-end-offset [+] MOV
-    tib-stack-base-offset [] tib-temp tib-segment MOV
-    ! Save callstack limit in TIB
-    tib-temp ctx-reg context-callstack-seg-offset [+] MOV
-    tib-temp tib-temp segment-start-offset [+] MOV
-    tib-stack-limit-offset [] tib-temp tib-segment MOV ;
index b36364a4d6f4d35a2f7d0e837341eee4e2515a69..04c34f9609ab5858d83f19653bf598dc4a244473 100755 (executable)
@@ -18,14 +18,14 @@ H{ } clone sub-primitives set
 "vocab:bootstrap/syntax.factor" parse-file
 
 architecture get {
-    { "windows-x86.32" "x86/32/windows" }
-    { "windows-x86.64" "x86/64/windows" }
-    { "unix-x86.32"  "x86/32/unix"  }
-    { "unix-x86.64"  "x86/64/unix"  }
-    { "linux-ppc.32" "ppc/32/linux" }
-    { "linux-ppc.64" "ppc/64/linux" }
+    { "windows-x86.32" "x86.32.windows" }
+    { "windows-x86.64" "x86.64.windows" }
+    { "unix-x86.32"  "x86.32.unix"  }
+    { "unix-x86.64"  "x86.64.unix"  }
+    { "linux-ppc.32" "ppc.32.linux" }
+    { "linux-ppc.64" "ppc.64.linux" }
 } ?at [ "Bad architecture: " prepend throw ] unless
-"vocab:cpu/" "/bootstrap.factor" surround parse-file
+"vocab:bootstrap/assembler/" ".factor" surround parse-file
 
 "vocab:bootstrap/layouts/layouts.factor" parse-file
 
index 495922b8402272a1d713db10da354eff32609b0a..38dcb7700a51e0936368b0838670fd405be586a8 100644 (file)
@@ -3,7 +3,7 @@ namespace factor {
 #define FACTOR_CPU_STRING "x86.32"
 
 /* Must match the leaf-stack-frame-size, signal-handler-stack-frame-size,
-and stack-frame-size constants in cpu/x86/32/bootstrap.factor */
+and stack-frame-size constants in bootstrap/assembler/x86.32.factor */
 static const unsigned LEAF_FRAME_SIZE = 16;
 static const unsigned SIGNAL_HANDLER_STACK_FRAME_SIZE = 48;
 static const unsigned JIT_FRAME_SIZE = 32;
index 662ffca9bbc8ab12c412f0798168484f58f6a3ea..614e9420f8c8dd03c0ee53b3d34aded50780b214 100644 (file)
@@ -28,7 +28,7 @@ inline static void uap_clear_fpu_status(void* uap) {
 #define UAP_STACK_POINTER_TYPE greg_t
 
 /* Must match the leaf-stack-frame-size, signal-handler-stack-frame-size,
-and stack-frame-size constants in basis/cpu/x86/64/unix/bootstrap.factor */
+and stack-frame-size constants in bootstrap/assembler/x86.64.unix.factor */
 static const unsigned LEAF_FRAME_SIZE = 16;
 static const unsigned SIGNAL_HANDLER_STACK_FRAME_SIZE = 160;
 static const unsigned JIT_FRAME_SIZE = 32;
index 7ae3cb8d1b0e3e31df520036189c4197f4a28db9..d1787bf6b937f64474ee2302047c796759fb4d81 100644 (file)
@@ -68,7 +68,7 @@ inline static void uap_clear_fpu_status(void* uap) {
 }
 
 /* Must match the leaf-stack-frame-size, signal-handler-stack-frame-size,
-and stack-frame-size constants in basis/cpu/x86/64/unix/bootstrap.factor */
+and stack-frame-size constants in basis/bootstrap/assembler/x86.64.unix.factor */
 static const unsigned LEAF_FRAME_SIZE = 16;
 static const unsigned SIGNAL_HANDLER_STACK_FRAME_SIZE = 160;
 static const unsigned JIT_FRAME_SIZE = 32;
index c564e13958016e792e7e4ef904eb4549b9764368..244aa0a7a4aad0954ef503b658280d5eb9fa4925 100644 (file)
@@ -3,7 +3,7 @@
 namespace factor {
 
 void factor_vm::c_to_factor_toplevel(cell quot) {
-  /* 32-bit Windows SEH set up in basis/cpu/x86/32/windows/bootstrap.factor */
+  /* 32-bit Windows SEH set up in basis/bootstrap/assembler/x86.32.windows.factor */
   c_to_factor(quot);
 }
 
index ef4c8cae4131b3084e6b850437862bafb179a89b..06a0d33bb58785566773a7e57a2cc6bb9b9e576a 100644 (file)
@@ -8,8 +8,7 @@ namespace factor {
 #define MXCSR(ctx) (ctx)->MxCsr
 
 /* Must match the leaf-stack-frame-size, signal-handler-stack-frame-size,
-and stack-frame-size constants in basis/cpu/x86/64/windows/bootstrap.factor */
-
+and stack-frame-size constants in basis/bootstap/assembler/x86.64.windows.factor */
 static const unsigned LEAF_FRAME_SIZE = 16;
 static const unsigned SIGNAL_HANDLER_STACK_FRAME_SIZE = 192;
 static const unsigned JIT_FRAME_SIZE = 64;
index 8deeecdeb283cd0bd79733e1ea203d5e159095b3..45f3aa074f7892aed20d5dab3479774100bfc264 100644 (file)
@@ -8,9 +8,10 @@ This is one of the two compilers implementing Factor; the second one is written
 in Factor and performs advanced optimizations. See
 basis/compiler/compiler.factor.
 
-The non-optimizing compiler compiles a quotation at a time by concatenating
-machine code chunks; prolog, epilog, call word, jump to word, etc. These machine
-code chunks are generated from Factor code in basis/cpu/.../bootstrap.factor.
+The non-optimizing compiler compiles a quotation at a time by
+concatenating machine code chunks; prolog, epilog, call word, jump to
+word, etc. These machine code chunks are generated from Factor code in
+basis/bootstrap/assembler/.
 
 Calls to words and constant quotations (referenced by conditionals and dips)
 are direct jumps to machine code blocks. Literals are also referenced directly