Do tuple reshaping at the end of a compilation unit, preserving a consistent view of the heap to code running during compilation
parent
b58d61a541
commit
d2c5f28b65
|
@ -87,7 +87,7 @@ $nl
|
|||
HELP: alien-invoke-error
|
||||
{ $error-description "Thrown if the word calling " { $link alien-invoke } " was not compiled with the optimizing compiler. This may be a result of one of several failure conditions:"
|
||||
{ $list
|
||||
{ "This can happen when experimenting with " { $link alien-invoke } " in this listener. To fix the problem, place the " { $link alien-invoke } " call in a word and then call " { $link recompile } ". See " { $link "compiler" } "." }
|
||||
{ "This can happen when experimenting with " { $link alien-invoke } " in this listener. To fix the problem, place the " { $link alien-invoke } " call in a word; word definitions are automatically compiled with the optimizing compiler." }
|
||||
{ "The return type or parameter list references an unknown C type." }
|
||||
{ "The symbol or library could not be found." }
|
||||
{ "One of the four inputs to " { $link alien-invoke } " is not a literal value. To call functions which are not known at compile-time, use " { $link alien-indirect } "." }
|
||||
|
@ -103,7 +103,7 @@ HELP: alien-invoke
|
|||
HELP: alien-indirect-error
|
||||
{ $error-description "Thrown if the word calling " { $link alien-indirect } " was not compiled with the optimizing compiler. This may be a result of one of several failure conditions:"
|
||||
{ $list
|
||||
{ "This can happen when experimenting with " { $link alien-indirect } " in this listener. To fix the problem, place the " { $link alien-indirect } " call in a word and then call " { $link recompile } ". See " { $link "compiler" } "." }
|
||||
{ "This can happen when experimenting with " { $link alien-indirect } " in this listener. To fix the problem, place the " { $link alien-indirect } " call in a word; word definitions are automatically compiled with the optimizing compiler." }
|
||||
{ "The return type or parameter list references an unknown C type." }
|
||||
{ "One of the three inputs to " { $link alien-indirect } " is not a literal value." }
|
||||
}
|
||||
|
@ -120,7 +120,7 @@ HELP: alien-indirect
|
|||
HELP: alien-callback-error
|
||||
{ $error-description "Thrown if the word calling " { $link alien-callback } " was not compiled with the optimizing compiler. This may be a result of one of several failure conditions:"
|
||||
{ $list
|
||||
{ "This can happen when experimenting with " { $link alien-callback } " in this listener. To fix the problem, place the " { $link alien-callback } " call in a word and then call " { $link recompile } ". See " { $link "compiler" } "." }
|
||||
{ "This can happen when experimenting with " { $link alien-callback } " in this listener. To fix the problem, place the " { $link alien-callback } " call in a word; word definitions are automatically compiled with the optimizing compiler." }
|
||||
{ "The return type or parameter list references an unknown C type." }
|
||||
{ "One of the four inputs to " { $link alien-callback } " is not a literal value." }
|
||||
}
|
||||
|
@ -199,9 +199,7 @@ ARTICLE: "alien-invoke" "Calling C from Factor"
|
|||
{ $subsection alien-invoke }
|
||||
"Sometimes it is necessary to invoke a C function pointer, rather than a named C function:"
|
||||
{ $subsection alien-indirect }
|
||||
"There are some details concerning the conversion of Factor objects to C values, and vice versa. See " { $link "c-data" } "."
|
||||
$nl
|
||||
"Don't forget to compile your binding word after defining it; C library calls cannot be made from an interpreted definition. Words defined in source files are automatically compiled when the source file is loaded, but words defined in the listener are not; when interactively testing C libraries, use " { $link compile } " or " { $link recompile } " to compile binding words." ;
|
||||
"There are some details concerning the conversion of Factor objects to C values, and vice versa. See " { $link "c-data" } "." ;
|
||||
|
||||
ARTICLE: "alien-callback-gc" "Callbacks and code GC"
|
||||
"A callback consits of two parts; the callback word, which pushes the address of the callback on the stack when executed, and the callback body itself. If the callback word is redefined, removed from the dictionary using " { $link forget } ", or recompiled, the callback body will not be reclaimed by the garbage collector, since potentially C code may be holding a reference to the callback body."
|
||||
|
|
|
@ -16,6 +16,14 @@ IN: bootstrap.compiler
|
|||
|
||||
"cpu." cpu append require
|
||||
|
||||
: enable-compiler ( -- )
|
||||
[ optimized-recompile-hook ] recompile-hook set-global ;
|
||||
|
||||
: disable-compiler ( -- )
|
||||
[ default-recompile-hook ] recompile-hook set-global ;
|
||||
|
||||
enable-compiler
|
||||
|
||||
nl
|
||||
"Compiling some words to speed up bootstrap..." write flush
|
||||
|
||||
|
@ -74,12 +82,4 @@ nl
|
|||
malloc free memcpy
|
||||
} compile
|
||||
|
||||
: enable-compiler ( -- )
|
||||
[ compiled-usages recompile ] recompile-hook set-global ;
|
||||
|
||||
: disable-compiler ( -- )
|
||||
[ default-recompile-hook ] recompile-hook set-global ;
|
||||
|
||||
enable-compiler
|
||||
|
||||
" done" print flush
|
||||
|
|
|
@ -30,7 +30,7 @@ crossref off
|
|||
"syntax" vocab vocab-words bootstrap-syntax set
|
||||
H{ } clone dictionary set
|
||||
H{ } clone changed-words set
|
||||
[ drop ] recompile-hook set
|
||||
[ default-recompile-hook ] recompile-hook set
|
||||
|
||||
call
|
||||
call
|
||||
|
|
|
@ -1,18 +1,14 @@
|
|||
USING: generator help.markup help.syntax words io parser
|
||||
assocs words.private sequences ;
|
||||
assocs words.private sequences compiler.units ;
|
||||
IN: compiler
|
||||
|
||||
ARTICLE: "compiler-usage" "Calling the optimizing compiler"
|
||||
"Normally, new word definitions are recompiled automatically, however in some circumstances the optimizing compiler may need to be called directly."
|
||||
$nl
|
||||
"The main entry points to the optimizing compiler:"
|
||||
{ $subsection compile }
|
||||
{ $subsection recompile }
|
||||
{ $subsection recompile-all }
|
||||
"The main entry point to the optimizing compiler:"
|
||||
{ $subsection optimized-recompile-hook }
|
||||
"Removing a word's optimized definition:"
|
||||
{ $subsection decompile }
|
||||
"The optimizing compiler can also compile and call a single quotation:"
|
||||
{ $subsection compile-call } ;
|
||||
{ $subsection decompile } ;
|
||||
|
||||
ARTICLE: "compiler" "Optimizing compiler"
|
||||
"Factor is a fully compiled language implementation with two distinct compilers:"
|
||||
|
@ -26,22 +22,6 @@ ARTICLE: "compiler" "Optimizing compiler"
|
|||
|
||||
ABOUT: "compiler"
|
||||
|
||||
HELP: compile
|
||||
{ $values { "seq" "a sequence of words" } }
|
||||
{ $description "Compiles a set of words. Ignores words which are already compiled." } ;
|
||||
|
||||
HELP: recompile
|
||||
{ $values { "seq" "a sequence of words" } }
|
||||
{ $description "Compiles a set of words. Re-compiles words which are already compiled." } ;
|
||||
|
||||
HELP: compile-call
|
||||
{ $values { "quot" "a quotation" } }
|
||||
{ $description "Compiles and runs a quotation." }
|
||||
{ $errors "Throws an error if the stack effect of the quotation cannot be inferred." } ;
|
||||
|
||||
HELP: recompile-all
|
||||
{ $description "Recompiles all words." } ;
|
||||
|
||||
HELP: decompile
|
||||
{ $values { "word" word } }
|
||||
{ $description "Removes a word's optimized definition. The word will be compiled with the non-optimizing compiler until recompiled with the optimizing compiler again." } ;
|
||||
|
@ -50,3 +30,8 @@ HELP: (compile)
|
|||
{ $values { "word" word } }
|
||||
{ $description "Compile a single word." }
|
||||
{ $notes "This is an internal word, and user code should call " { $link compile } " instead." } ;
|
||||
|
||||
HELP: optimized-recompile-hook
|
||||
{ $values { "words" "a sequence of words" } { "alist" "an association list" } }
|
||||
{ $description "Compile a set of words." }
|
||||
{ $notes "This is an internal word, and user code should call " { $link compile } " instead." } ;
|
||||
|
|
|
@ -4,7 +4,7 @@ USING: kernel namespaces arrays sequences io inference.backend
|
|||
inference.state generator debugger math.parser prettyprint words
|
||||
compiler.units continuations vocabs assocs alien.compiler dlists
|
||||
optimizer definitions math compiler.errors threads graphs
|
||||
generic ;
|
||||
generic inference ;
|
||||
IN: compiler
|
||||
|
||||
: compiled-usages ( words -- seq )
|
||||
|
@ -49,27 +49,17 @@ IN: compiler
|
|||
compile-loop
|
||||
] if ;
|
||||
|
||||
: recompile ( words -- )
|
||||
: decompile ( word -- )
|
||||
f 2array 1array t modify-code-heap ;
|
||||
|
||||
: optimized-recompile-hook ( words -- alist )
|
||||
[
|
||||
H{ } clone compile-queue set
|
||||
H{ } clone compiled set
|
||||
[ queue-compile ] each
|
||||
compiled-usages [ queue-compile ] each
|
||||
compile-queue get compile-loop
|
||||
compiled get >alist
|
||||
dup [ drop crossref? ] assoc-contains?
|
||||
modify-code-heap
|
||||
] with-scope ; inline
|
||||
|
||||
: compile ( words -- )
|
||||
[ compiled? not ] subset recompile ;
|
||||
|
||||
: compile-call ( quot -- )
|
||||
H{ } clone changed-words
|
||||
[ define-temp dup 1array compile ] with-variable
|
||||
execute ;
|
||||
] with-scope ;
|
||||
|
||||
: recompile-all ( -- )
|
||||
[ all-words recompile ] with-compiler-errors ;
|
||||
|
||||
: decompile ( word -- )
|
||||
f 2array 1array t modify-code-heap ;
|
||||
forget-errors all-words compile ;
|
||||
|
|
|
@ -61,3 +61,11 @@ HELP: modify-code-heap ( alist -- )
|
|||
{ { $snippet "{ code labels rel words literals }" } " - in this case, a code heap block is allocated with the given data." }
|
||||
} }
|
||||
{ $notes "This word is called at the end of " { $link with-compilation-unit } "." } ;
|
||||
|
||||
HELP: compile
|
||||
{ $values { "seq" "a sequence of words" } }
|
||||
{ $description "Compiles a set of words." } ;
|
||||
|
||||
HELP: compile-call
|
||||
{ $values { "quot" "a quotation" } }
|
||||
{ $description "Compiles and runs a quotation." } ;
|
||||
|
|
|
@ -63,24 +63,39 @@ GENERIC: definitions-changed ( assoc obj -- )
|
|||
dup changed-words get update
|
||||
dup dup changed-vocabs update ;
|
||||
|
||||
: compile ( words -- )
|
||||
recompile-hook get call
|
||||
dup [ drop crossref? ] assoc-contains?
|
||||
modify-code-heap ;
|
||||
|
||||
SYMBOL: post-compile-tasks
|
||||
|
||||
: after-compilation ( quot -- )
|
||||
post-compile-tasks get push ;
|
||||
|
||||
: finish-compilation-unit ( -- )
|
||||
changed-words get keys recompile-hook get call
|
||||
dup [ drop crossref? ] assoc-contains?
|
||||
post-compile-tasks get [ call ] each
|
||||
modify-code-heap
|
||||
changed-definitions notify-definition-observers ;
|
||||
|
||||
: with-compilation-unit ( quot -- )
|
||||
[
|
||||
H{ } clone changed-words set
|
||||
H{ } clone forgotten-definitions set
|
||||
V{ } clone post-compile-tasks set
|
||||
<definitions> new-definitions set
|
||||
<definitions> old-definitions set
|
||||
[ finish-compilation-unit ]
|
||||
[ ] cleanup
|
||||
] with-scope ; inline
|
||||
|
||||
: default-recompile-hook
|
||||
[ f ] { } map>assoc
|
||||
dup [ drop crossref? ] assoc-contains?
|
||||
modify-code-heap ;
|
||||
: compile-call ( quot -- )
|
||||
[ define-temp ] with-compilation-unit execute ;
|
||||
|
||||
: default-recompile-hook ( words -- alist )
|
||||
[ f ] { } map>assoc ;
|
||||
|
||||
recompile-hook global
|
||||
[ [ default-recompile-hook ] or ]
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
! Copyright (C) 2005, 2007 Slava Pestov.
|
||||
! Copyright (C) 2005, 2008 Slava Pestov.
|
||||
! See http://factorcode.org/license.txt for BSD license.
|
||||
USING: alien.c-types arrays cpu.x86.assembler
|
||||
cpu.x86.architecture cpu.x86.intrinsics cpu.x86.allot
|
||||
cpu.architecture kernel kernel.private math namespaces sequences
|
||||
generator.registers generator.fixup generator system
|
||||
alien.compiler combinators command-line
|
||||
compiler io vocabs.loader ;
|
||||
compiler compiler.units io vocabs.loader ;
|
||||
IN: cpu.x86.32
|
||||
|
||||
PREDICATE: x86-backend x86-32-backend
|
||||
|
@ -281,7 +281,10 @@ T{ x86-backend f 4 } compiler-backend set-global
|
|||
|
||||
"-no-sse2" cli-args member? [
|
||||
"Checking if your CPU supports SSE2..." print flush
|
||||
[ sse2? ] compile-call [
|
||||
[ optimized-recompile-hook ] recompile-hook [
|
||||
[ sse2? ] compile-call
|
||||
] with-variable
|
||||
[
|
||||
" - yes" print
|
||||
"cpu.x86.sse2" require
|
||||
] [
|
||||
|
|
|
@ -47,8 +47,8 @@ HELP: gc-time ( -- n )
|
|||
{ $values { "n" "a timestamp in milliseconds" } }
|
||||
{ $description "Outputs the total time spent in garbage collection during this Factor session." } ;
|
||||
|
||||
HELP: data-room ( -- cards semi generations )
|
||||
{ $values { "cards" "number of bytes reserved for card marking" } { "semi" "number of bytes reserved for tenured semi-space" } { "generations" "array of free/total bytes pairs" } }
|
||||
HELP: data-room ( -- cards generations )
|
||||
{ $values { "cards" "number of bytes reserved for card marking" } { "generations" "array of free/total bytes pairs" } }
|
||||
{ $description "Queries the runtime for memory usage information." } ;
|
||||
|
||||
HELP: code-room ( -- code-free code-total )
|
||||
|
|
|
@ -237,3 +237,40 @@ C: <erg's-reshape-problem> erg's-reshape-problem
|
|||
[
|
||||
"IN: temporary SYMBOL: not-a-class C: <not-a-class> not-a-class" eval
|
||||
] [ [ check-tuple? ] is? ] must-fail-with
|
||||
|
||||
! Hardcore unit tests
|
||||
USE: threads
|
||||
|
||||
\ thread "slot-names" word-prop "slot-names" set
|
||||
|
||||
[ ] [
|
||||
[
|
||||
\ thread { "xxx" } "slot-names" get append
|
||||
define-tuple-class
|
||||
] with-compilation-unit
|
||||
|
||||
[ 1337 sleep ] "Test" spawn drop
|
||||
|
||||
[
|
||||
\ thread "slot-names" get
|
||||
define-tuple-class
|
||||
] with-compilation-unit
|
||||
] unit-test
|
||||
|
||||
USE: vocabs
|
||||
|
||||
\ vocab "slot-names" word-prop "slot-names" set
|
||||
|
||||
[ ] [
|
||||
[
|
||||
\ vocab { "xxx" } "slot-names" get append
|
||||
define-tuple-class
|
||||
] with-compilation-unit
|
||||
|
||||
all-words drop
|
||||
|
||||
[
|
||||
\ vocab "slot-names" get
|
||||
define-tuple-class
|
||||
] with-compilation-unit
|
||||
] unit-test
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
USING: arrays definitions hashtables kernel
|
||||
kernel.private math namespaces sequences sequences.private
|
||||
strings vectors words quotations memory combinators generic
|
||||
classes classes.private slots slots.private ;
|
||||
classes classes.private slots slots.private compiler.units ;
|
||||
IN: tuples
|
||||
|
||||
M: tuple delegate 3 slot ;
|
||||
|
@ -35,9 +35,12 @@ M: tuple class class-of-tuple ;
|
|||
append (>tuple) ;
|
||||
|
||||
: reshape-tuples ( class newslots -- )
|
||||
>r dup [ swap class eq? ] curry instances dup
|
||||
rot "slot-names" word-prop r> permutation
|
||||
[ reshape-tuple ] curry map become ;
|
||||
>r dup "slot-names" word-prop r> permutation
|
||||
[
|
||||
>r [ swap class eq? ] curry instances dup r>
|
||||
[ reshape-tuple ] curry map
|
||||
become
|
||||
] 2curry after-compilation ;
|
||||
|
||||
: old-slots ( class newslots -- seq )
|
||||
swap "slots" word-prop 1 tail-slice
|
||||
|
@ -55,6 +58,7 @@ M: tuple class class-of-tuple ;
|
|||
over "slot-names" word-prop over = [
|
||||
2dup forget-slots
|
||||
2dup reshape-tuples
|
||||
over changed-word
|
||||
over redefined
|
||||
] unless
|
||||
] when 2drop ;
|
||||
|
|
|
@ -76,9 +76,9 @@ $nl
|
|||
ARTICLE: "declarations" "Declarations"
|
||||
"Declarations give special behavior to a word. Declarations are parsing words that set a word property in the most recently defined word."
|
||||
$nl
|
||||
"The first declaration specifies the time when a word runs. It affects both interpreted and compiled definitions."
|
||||
"The first declaration specifies the time when a word runs. It affects both the non-optimizing and optimizing compilers:"
|
||||
{ $subsection POSTPONE: parsing }
|
||||
"The remaining declarations only affect compiled definitions. They do not change evaluation semantics of a word, but instead declare that the word follows a certain contract, and thus may be compiled differently."
|
||||
"The remaining declarations only affect definitions compiled with the optimizing compiler. They do not change evaluation semantics of a word, but instead declare that the word follows a certain contract, and thus may be compiled differently."
|
||||
{ $warning "If a generic word is declared " { $link POSTPONE: foldable } " or " { $link POSTPONE: flushable } ", all methods must satisfy the contract, otherwise unpredicable behavior will occur." }
|
||||
{ $subsection POSTPONE: inline }
|
||||
{ $subsection POSTPONE: foldable }
|
||||
|
|
Loading…
Reference in New Issue