Fix channels for recent changes
parent
743b62da22
commit
27656fe0e3
|
@ -2,7 +2,8 @@
|
|||
! See http://factorcode.org/license.txt for BSD license.
|
||||
!
|
||||
! Channels - based on ideas from newsqueak
|
||||
USING: kernel sequences sequences.lib threads continuations random math ;
|
||||
USING: kernel sequences sequences.lib threads continuations
|
||||
random math ;
|
||||
IN: channels
|
||||
|
||||
TUPLE: channel receivers senders ;
|
||||
|
@ -16,7 +17,8 @@ GENERIC: from ( channel -- value )
|
|||
<PRIVATE
|
||||
|
||||
: wait ( channel -- )
|
||||
[ channel-senders push stop ] curry callcc0 ;
|
||||
[ channel-senders push ] curry
|
||||
"channel send" suspend drop ;
|
||||
|
||||
: (to) ( value receivers -- )
|
||||
delete-random resume-with yield ;
|
||||
|
@ -24,8 +26,8 @@ GENERIC: from ( channel -- value )
|
|||
: notify ( continuation channel -- channel )
|
||||
[ channel-receivers push ] keep ;
|
||||
|
||||
: (from) ( senders -- * )
|
||||
delete-random continue ;
|
||||
: (from) ( senders -- )
|
||||
delete-random resume ;
|
||||
|
||||
PRIVATE>
|
||||
|
||||
|
@ -36,5 +38,5 @@ M: channel to ( value channel -- )
|
|||
M: channel from ( channel -- value )
|
||||
[
|
||||
notify channel-senders
|
||||
dup empty? [ stop ] [ (from) ] if
|
||||
] curry callcc1 ;
|
||||
dup empty? [ drop ] [ (from) ] if
|
||||
] curry "channel receive" suspend ;
|
||||
|
|
|
@ -1,31 +0,0 @@
|
|||
! Copyright (C) 2004, 2007 Slava Pestov.
|
||||
! See http://factorcode.org/license.txt for BSD license.
|
||||
USING: tools.interpreter kernel arrays continuations threads
|
||||
sequences namespaces ;
|
||||
IN: tools.interpreter.debug
|
||||
|
||||
: run-interpreter ( interpreter -- )
|
||||
dup interpreter-continuation [
|
||||
dup step-into run-interpreter
|
||||
] [
|
||||
drop
|
||||
] if ;
|
||||
|
||||
: quot>cont ( quot -- cont )
|
||||
[
|
||||
swap [
|
||||
continue-with
|
||||
] curry callcc0 call stop
|
||||
] curry callcc1 ;
|
||||
|
||||
: init-interpreter ( quot interpreter -- )
|
||||
>r
|
||||
[ datastack "datastack" set ] compose quot>cont
|
||||
f swap 2array
|
||||
r> restore ;
|
||||
|
||||
: test-interpreter ( quot -- )
|
||||
<interpreter>
|
||||
[ init-interpreter ] keep
|
||||
run-interpreter
|
||||
"datastack" get ;
|
|
@ -1,54 +0,0 @@
|
|||
USING: help.markup help.syntax kernel generic
|
||||
math hashtables quotations classes continuations ;
|
||||
IN: tools.interpreter
|
||||
|
||||
ARTICLE: "meta-interpreter" "Meta-circular interpreter"
|
||||
"The meta-circular interpreter is used to implement the walker tool in the UI. If you are simply interested in single stepping through a piece of code, use the " { $link "ui-walker" } "."
|
||||
$nl
|
||||
"On the other hand, if you want to implement a similar tool yourself, then you can use the words described in this section."
|
||||
$nl
|
||||
"Meta-circular interpreter words are found in the " { $vocab-link "tools.interpreter" } " vocabulary."
|
||||
$nl
|
||||
"Breakpoints can be inserted in user code:"
|
||||
{ $subsection break }
|
||||
"Breakpoints invoke a hook:"
|
||||
{ $subsection break-hook }
|
||||
"Single stepping with the meta-circular interpreter:"
|
||||
{ $subsection step }
|
||||
{ $subsection step-into }
|
||||
{ $subsection step-out }
|
||||
{ $subsection step-all } ;
|
||||
|
||||
ABOUT: "meta-interpreter"
|
||||
|
||||
HELP: interpreter
|
||||
{ $class-description "An interpreter instance." } ;
|
||||
|
||||
HELP: step
|
||||
{ $values { "interpreter" interpreter } }
|
||||
{ $description "Evaluates the object in the single stepper using Factor evaluation semantics:"
|
||||
{ $list
|
||||
{ "If the object is a " { $link wrapper } ", then the wrapped object is pushed on the single stepper's data stack" }
|
||||
{ "If the object is a word, then the word is executed in the single stepper's continuation atomically" }
|
||||
{ "Otherwise, the object is pushed on the single stepper's data stack" }
|
||||
}
|
||||
} ;
|
||||
|
||||
HELP: step-into
|
||||
{ $values { "interpreter" interpreter } }
|
||||
{ $description "Evaluates the object in the single stepper using Factor evaluation semantics:"
|
||||
{ $list
|
||||
{ "If the object is a " { $link wrapper } ", then the wrapped object is pushed on the single stepper's data stack" }
|
||||
{ "If the object is a compound word, then the single stepper enters the word definition" }
|
||||
{ "If the object is a primitive word or a word with special single stepper behavior, it is executed in the single stepper's continuation atomically" }
|
||||
{ "Otherwise, the object is pushed on the single stepper's data stack" }
|
||||
}
|
||||
} ;
|
||||
|
||||
HELP: step-out
|
||||
{ $values { "interpreter" interpreter } }
|
||||
{ $description "Evaluates the remainder of the current quotation in the single stepper." } ;
|
||||
|
||||
HELP: step-all
|
||||
{ $values { "interpreter" interpreter } }
|
||||
{ $description "Executes the remainder of the single stepper's continuation. This effectively ends single stepping unless the continuation invokes " { $link break } " at a later point in time." } ;
|
|
@ -1,113 +0,0 @@
|
|||
USING: tools.interpreter io io.streams.string kernel math
|
||||
math.private namespaces prettyprint sequences tools.test
|
||||
continuations math.parser threads arrays
|
||||
tools.interpreter.private tools.interpreter.debug ;
|
||||
IN: temporary
|
||||
|
||||
[ "Ooops" throw ] break-hook set
|
||||
|
||||
[ { } ] [
|
||||
[ ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { 1 } ] [
|
||||
[ 1 ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { 1 2 3 } ] [
|
||||
[ 1 2 3 ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { "Yo" 2 } ] [
|
||||
[ 2 >r "Yo" r> ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { 2 } ] [
|
||||
[ t [ 2 ] [ "hi" ] if ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { "hi" } ] [
|
||||
[ f [ 2 ] [ "hi" ] if ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { 4 } ] [
|
||||
[ 2 2 fixnum+ ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
: foo 2 2 fixnum+ ;
|
||||
|
||||
[ { 8 } ] [
|
||||
[ foo 4 fixnum+ ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { C{ 1 1.5 } { } C{ 1 1.5 } { } } ] [
|
||||
[ C{ 1 1.5 } { } 2dup ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { t } ] [
|
||||
[ 5 5 number= ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { f } ] [
|
||||
[ 5 6 number= ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { f } ] [
|
||||
[ "XYZ" "XYZ" mismatch ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { t } ] [
|
||||
[ "XYZ" "XYZ" sequence= ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { t } ] [
|
||||
[ "XYZ" "XYZ" = ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { f } ] [
|
||||
[ "XYZ" "XuZ" = ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { 4 } ] [
|
||||
[ 2 2 + ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { } 2 ] [
|
||||
2 "x" set [ [ 3 "x" set ] with-scope ] test-interpreter "x" get
|
||||
] unit-test
|
||||
|
||||
[ { 3 } ] [
|
||||
[ 3 "x" set "x" get ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { "hi\n" } ] [
|
||||
[ [ "hi" print ] with-string-writer ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { "4\n" } ] [
|
||||
[ [ 2 2 + number>string print ] with-string-writer ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { 1 2 3 } ] [
|
||||
[ { 1 2 3 } set-datastack ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { 6 } ]
|
||||
[ [ 3 [ nip continue ] callcc0 2 * ] test-interpreter ] unit-test
|
||||
|
||||
[ { 6 } ]
|
||||
[ [ [ 3 swap continue-with ] callcc1 2 * ] test-interpreter ] unit-test
|
||||
|
||||
[ { } ]
|
||||
[ [ [ ] [ ] recover ] test-interpreter ] unit-test
|
||||
|
||||
[ { 6 } ]
|
||||
[ [ [ 3 throw ] [ 2 * ] recover ] test-interpreter ] unit-test
|
||||
|
||||
[ { "{ 1 2 3 }\n" } ] [
|
||||
[ [ { 1 2 3 } . ] with-string-writer ] test-interpreter
|
||||
] unit-test
|
||||
|
||||
[ { } ] [
|
||||
[ "a" "b" set "c" "d" set [ ] test-interpreter ] with-scope
|
||||
] unit-test
|
|
@ -0,0 +1,19 @@
|
|||
! Copyright (C) 2004, 2008 Slava Pestov.
|
||||
! See http://factorcode.org/license.txt for BSD license.
|
||||
USING: concurrency.promises models tools.walker kernel
|
||||
sequences concurrency.messaging locals ;
|
||||
IN: tools.walker.debug
|
||||
|
||||
:: test-walker | quot |
|
||||
[let | p [ <promise> ]
|
||||
s [ f <model> ]
|
||||
c [ f <model> ] |
|
||||
[ s c start-walker-thread p fulfill break ]
|
||||
quot compose
|
||||
|
||||
step-into-all
|
||||
p ?promise
|
||||
send-synchronous drop
|
||||
|
||||
c model-value continuation-data
|
||||
] ;
|
|
@ -0,0 +1 @@
|
|||
|
|
@ -0,0 +1,106 @@
|
|||
USING: tools.walker io io.streams.string kernel math
|
||||
math.private namespaces prettyprint sequences tools.test
|
||||
continuations math.parser threads arrays tools.walker.debug ;
|
||||
IN: temporary
|
||||
|
||||
[ { } ] [
|
||||
[ ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { 1 } ] [
|
||||
[ 1 ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { 1 2 3 } ] [
|
||||
[ 1 2 3 ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { "Yo" 2 } ] [
|
||||
[ 2 >r "Yo" r> ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { 2 } ] [
|
||||
[ t [ 2 ] [ "hi" ] if ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { "hi" } ] [
|
||||
[ f [ 2 ] [ "hi" ] if ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { 4 } ] [
|
||||
[ 2 2 fixnum+ ] test-walker
|
||||
] unit-test
|
||||
|
||||
: foo 2 2 fixnum+ ;
|
||||
|
||||
[ { 8 } ] [
|
||||
[ foo 4 fixnum+ ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { C{ 1 1.5 } { } C{ 1 1.5 } { } } ] [
|
||||
[ C{ 1 1.5 } { } 2dup ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { t } ] [
|
||||
[ 5 5 number= ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { f } ] [
|
||||
[ 5 6 number= ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { f } ] [
|
||||
[ "XYZ" "XYZ" mismatch ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { t } ] [
|
||||
[ "XYZ" "XYZ" sequence= ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { t } ] [
|
||||
[ "XYZ" "XYZ" = ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { f } ] [
|
||||
[ "XYZ" "XuZ" = ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { 4 } ] [
|
||||
[ 2 2 + ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { 3 } ] [
|
||||
[ [ 3 "x" set "x" get ] with-scope ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { "hi\n" } ] [
|
||||
[ [ "hi" print ] with-string-writer ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { "4\n" } ] [
|
||||
[ [ 2 2 + number>string print ] with-string-writer ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { 1 2 3 } ] [
|
||||
[ { 1 2 3 } set-datastack ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { 6 } ]
|
||||
[ [ 3 [ nip continue ] callcc0 2 * ] test-walker ] unit-test
|
||||
|
||||
[ { 6 } ]
|
||||
[ [ [ 3 swap continue-with ] callcc1 2 * ] test-walker ] unit-test
|
||||
|
||||
[ { } ]
|
||||
[ [ [ ] [ ] recover ] test-walker ] unit-test
|
||||
|
||||
[ { 6 } ]
|
||||
[ [ [ 3 throw ] [ 2 * ] recover ] test-walker ] unit-test
|
||||
|
||||
[ { "{ 1 2 3 }\n" } ] [
|
||||
[ [ { 1 2 3 } . ] with-string-writer ] test-walker
|
||||
] unit-test
|
||||
|
||||
[ { } ] [
|
||||
[ "a" "b" set "c" "d" set [ ] test-walker ] with-scope
|
||||
] unit-test
|
|
@ -1,54 +1,54 @@
|
|||
: walk ( quot -- ) \ break add* call ;
|
||||
! Copyright (C) 2004, 2008 Slava Pestov.
|
||||
! See http://factorcode.org/license.txt for BSD license.
|
||||
USING: threads kernel namespaces continuations combinators
|
||||
sequences math namespaces.private continuations.private
|
||||
concurrency.messaging quotations kernel.private words
|
||||
sequences.private assocs models ;
|
||||
IN: tools.walker
|
||||
|
||||
SYMBOL: walker-hook
|
||||
|
||||
! Thread local
|
||||
SYMBOL: interpreter-thread
|
||||
SYMBOL: walker-thread
|
||||
|
||||
: get-interpreter-thread ( -- thread )
|
||||
interpreter-thread tget dup [
|
||||
walker-hook get
|
||||
[ "No walker hook" throw ] or
|
||||
interpreter-thread
|
||||
: get-walker-thread ( -- thread )
|
||||
walker-thread tget [
|
||||
walker-hook get [ "No walker hook" throw ] or call
|
||||
walker-thread tget
|
||||
] unless* ;
|
||||
|
||||
: break ( -- )
|
||||
callstack [
|
||||
over set-continuation-callstack
|
||||
over set-continuation-call
|
||||
|
||||
interpreter-thread send-synchronous {
|
||||
get-walker-thread send-synchronous {
|
||||
{ [ dup continuation? ] [ (continue) ] }
|
||||
{ [ dup quotation? ] [ call ] }
|
||||
{ [ dup not ] [ "Single stepping abandoned" throw ] }
|
||||
} cond
|
||||
] curry callcc0 ;
|
||||
|
||||
SYMBOL: +suspended+
|
||||
SYMBOL: +running+
|
||||
SYMBOL: +stopped+
|
||||
|
||||
! Messages sent to interpreter thread
|
||||
SYMBOL: status
|
||||
: walk ( quot -- ) \ break add* call ;
|
||||
|
||||
! Messages sent to walker thread
|
||||
SYMBOL: step
|
||||
SYMBOL: step-out
|
||||
SYMBOL: step-into
|
||||
SYMBOL: step-all
|
||||
SYMBOL: step-into-all
|
||||
SYMBOL: step-back
|
||||
SYMBOL: detach
|
||||
SYMBOL: abandon
|
||||
SYMBOL: call-in
|
||||
|
||||
SYMBOL: get-thread
|
||||
SYMBOL: get-continuation
|
||||
|
||||
<PRIVATE
|
||||
|
||||
! Thread locals
|
||||
SYMBOL: interpreter-running?
|
||||
SYMBOL: interpreter-stepping?
|
||||
SYMBOL: interpreter-continuation
|
||||
SYMBOL: interpreter-history
|
||||
SYMBOL: walker-status
|
||||
SYMBOL: walker-continuation
|
||||
SYMBOL: walker-history
|
||||
|
||||
SYMBOL: +running+
|
||||
SYMBOL: +suspended+
|
||||
SYMBOL: +stopped+
|
||||
|
||||
: change-frame ( continuation quot -- continuation' )
|
||||
#! Applies quot to innermost call frame of the
|
||||
|
@ -112,7 +112,7 @@ M: word (step-into) (step-into-execute) ;
|
|||
{
|
||||
>n ndrop >c c>
|
||||
continue continue-with
|
||||
(continue-with) stop yield suspend sleep (spawn)
|
||||
stop yield suspend sleep (spawn)
|
||||
suspend
|
||||
} [
|
||||
dup [ execute break ] curry
|
||||
|
@ -126,102 +126,107 @@ M: word (step-into) (step-into-execute) ;
|
|||
swap cut [
|
||||
swap % unclip literalize , \ (step-into) , %
|
||||
] [ ] make
|
||||
] (step) ;
|
||||
] change-frame ;
|
||||
|
||||
: status-change ( symbol -- )
|
||||
+running+ interpreter-status tget set-model ;
|
||||
: status ( -- symbol )
|
||||
walker-status tget model-value ;
|
||||
|
||||
: set-status ( symbol -- )
|
||||
walker-status tget set-model ;
|
||||
|
||||
: detach-msg ( -- f )
|
||||
+detached+ status-change
|
||||
f interpreter-stepping? tset
|
||||
f interpreter-running? tset
|
||||
f ;
|
||||
+stopped+ set-status ;
|
||||
|
||||
: continuation-msg ( -- continuation )
|
||||
interpreter-thread tget thread-continuation box-value ;
|
||||
: keep-running ( continuation -- continuation )
|
||||
+running+ set-status
|
||||
dup continuation? [ dup walker-history tget push ] when ;
|
||||
|
||||
: keep-running f interpreter-stepping? tset ;
|
||||
: walker-stopped ( -- )
|
||||
+stopped+ set-status
|
||||
[
|
||||
{
|
||||
{ detach [ detach-msg ] }
|
||||
[ drop f ]
|
||||
} case
|
||||
] handle-synchronous
|
||||
walker-stopped ;
|
||||
|
||||
: save-continuation ( continuation -- )
|
||||
dup interpreter-continuation tget set-model
|
||||
interpreter-history tget push ;
|
||||
|
||||
: handle-command ( continuation -- continuation' )
|
||||
t interpreter-stepping? tset
|
||||
[ interpreter-stepping? tget ] [
|
||||
: step-into-all-loop ( -- )
|
||||
+running+ set-status
|
||||
[ status +stopped+ eq? not ] [
|
||||
[
|
||||
{
|
||||
! These are sent by the walker tool. We reply and
|
||||
! keep cycling.
|
||||
{ status [ +suspended+ ] }
|
||||
{ detach [ detach-msg ] }
|
||||
{ get-thread [ interpreter-thread tget ] }
|
||||
{ get-continuation [ dup ] }
|
||||
{ step [ f ] }
|
||||
{ step-out [ f ] }
|
||||
{ step-into [ f ] }
|
||||
{ step-all [ f ] }
|
||||
{ step-into-all [ f ] }
|
||||
{ step-back [ f ] }
|
||||
{ f [ walker-stopped ] }
|
||||
[ step-into-msg ]
|
||||
} case
|
||||
] handle-synchronous
|
||||
] [ ] while ;
|
||||
|
||||
: walker-suspended ( continuation -- continuation' )
|
||||
+suspended+ set-status
|
||||
[ status +suspended+ eq? ] [
|
||||
[
|
||||
{
|
||||
! These are sent by the walker tool. We reply
|
||||
! and keep cycling.
|
||||
{ detach [ detach-msg ] }
|
||||
! These change the state of the thread being
|
||||
! interpreted, so we modify the continuation and
|
||||
! output f.
|
||||
{ step [ (step) keep-running ] }
|
||||
{ step-out [ (step-out) keep-running ] }
|
||||
{ step-into [ (step-into) keep-running ] }
|
||||
{ step [ step-msg keep-running ] }
|
||||
{ step-out [ step-out-msg keep-running ] }
|
||||
{ step-into [ step-into-msg keep-running ] }
|
||||
{ step-all [ keep-running ] }
|
||||
{ step-into-all [ step-into-all-loop ] }
|
||||
{ abandon [ drop f keep-running ] }
|
||||
! Pass quotation to debugged thread
|
||||
{ call-in [ nip keep-running ] }
|
||||
! Pass previous continuation to debugged thread
|
||||
{ step-back [ drop interpreter-history tget pop f ] }
|
||||
{ step-back [ drop walker-history tget pop f ] }
|
||||
} case
|
||||
] handle-synchronous
|
||||
] [ ] while
|
||||
dup continuation? [ dup save-continuation ] when ;
|
||||
] [ ] while ;
|
||||
|
||||
: interpreter-stopped ( -- )
|
||||
[
|
||||
{
|
||||
{ detach [ detach-msg ] }
|
||||
{ status [ +stopped+ ] }
|
||||
{ get-thread [ interpreter-thread tget ] }
|
||||
{ get-continuation [ f ] }
|
||||
[ drop f ]
|
||||
} case
|
||||
] handle-synchronous
|
||||
interpreter-stopped ;
|
||||
|
||||
: interpreter-loop ( -- )
|
||||
[ interpreter-running? tget ] [
|
||||
: walker-loop ( -- )
|
||||
+running+ set-status
|
||||
[ status +stopped+ eq? not ] [
|
||||
[
|
||||
status-change
|
||||
{
|
||||
{ detach [ detach-msg ] }
|
||||
{ get-thread [ interpreter-thread tget ] }
|
||||
{ get-continuation [ f ] }
|
||||
! ignore these commands while the thread is
|
||||
! running
|
||||
{ step [ f ] }
|
||||
{ step-out [ f ] }
|
||||
{ step-into [ f ] }
|
||||
{ step-all [ f ] }
|
||||
{ step-into-all [ step-into-all-loop ] }
|
||||
{ step-back [ f ] }
|
||||
! thread has exited so we exit the monitor too
|
||||
{ f [ interpreter-stopped ] }
|
||||
{ f [ walker-stopped f ] }
|
||||
! thread hit a breakpoint and sent us the
|
||||
! continuation, so we modify it and send it back.
|
||||
[ handle-command ]
|
||||
! continuation, so we modify it and send it
|
||||
! back.
|
||||
[ walker-suspended ]
|
||||
} case
|
||||
] handle-synchronous
|
||||
] [ ] while;
|
||||
] [ ] while ;
|
||||
|
||||
PRIVATE>
|
||||
: associate-thread ( walker -- )
|
||||
dup walker-thread tset
|
||||
[ f swap send ] curry self set-thread-exit-handler ;
|
||||
|
||||
: start-interpreter-thread ( thread -- thread' )
|
||||
: start-walker-thread ( status continuation -- thread' )
|
||||
[
|
||||
[
|
||||
interpreter-thread tset
|
||||
t interpreter-running tset
|
||||
f interpreter-stepping tset
|
||||
f <model> interpreter-continuation tset
|
||||
V{ } clone interpreter-history tset
|
||||
interpreter-loop
|
||||
] curry
|
||||
] keep
|
||||
"Interpreter for " over thread-name append spawn
|
||||
dup rot set-thread-;
|
||||
walker-continuation tset
|
||||
walker-status tset
|
||||
V{ } clone walker-history tset
|
||||
walker-loop
|
||||
] 2curry
|
||||
"Walker on " self thread-name append spawn
|
||||
[ associate-thread ] keep ;
|
Loading…
Reference in New Issue