file: job.t package: muf status: alpha
The assembleTag
prim supports
implementation of non-local goto
operations
-- those which jump from one function to an
enclosing function, much like the C
longjmp()
library function.
The assembleTag
prim deposits an
instruction which at runtime will pop a tag from
the job's data stack and push a
JOB_STACKFRAME_TAG stackframe onto the job's
loop stack, containing the popped tag together
with the given label
: As long as that
stackframe exists, any goto
of that tag
will result in a transfer of control to the given
label
.
You may mark the end of the tag's scope by
popping the JOB_STACKFRAME_TAG stackframe
using the popTagframe
primitive.
For technical reasons relating to support for
the CommonLisp standard, any sequence of one
or more JOB_STACKFRAME_TAG stackframes
pushed on the loopstack should be topped off
with a JOB_STACKFRAME_TAGTOP frame: These
can be pushed and popped using
pushTagtopframe
and popTagtopframe
.
Here is an example which hand-compiles
: xx withTag qqq do{ ( Establish nonlocal goto target ) 'qqq goto ( Do nonlocal goto to 'tag' label ) "Hi mom!" ( This will get jumped over. ) qqq ( Specify tag label location. ) "Hi dad!" ( This will get executed. ) } ( End of tag scope. ) ;
stack: makeAssembler --> *asm* stack: *asm* reset stack: *asm* assembleLabelGet --> *label* ( Allocate label ) stack: 'qqq *asm* assembleConstant ( Code to push tag on stack ) stack: *label* *asm* assembleTag ( Code to push tagframe on stack ) stack: #'pushTagtopframe *asm* assembleCall ( Code to push tagtopframe on stack ) stack: 'qqq *asm* assembleConstant ( Code to again push tag on stack ) stack: #'goto *asm* assembleCall ( Code to do nonlocal goto ) stack: "Hi mom!" *asm* assembleConstant ( Code to get jumped over ) stack: *label* *asm* assembleLabel ( Label location ) stack: "Hi dad!" *asm* assembleConstant ( Code to get executed ) stack: #'popTagtopframe *asm* assembleCall ( Code to pop tagtopframe from stack ) stack: #'popTagframe *asm* assembleCall ( Code to end tag scope ) stack: nil -1 makeFunction *asm* finishAssembly --> #'xx ( Compile fn 'xx' ) stack: xx ( Invoke function ) stack: "Hi dad!"
Go to the first, previous, next, last section, table of contents.