[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

TAGBODY vs LABELS



    Date: Sun, 10 Aug 86 14:50:39 MDT
    From: shebs%utah-orion@utah-cs.arpa (Stanley Shebs)

    I was in the process of implementing TAGBODY in terms of LABELS (each
    piece of straightline code turns into a function, and GO turns into
    function calls), but upon perusing CLtl more closely, I found that
    the GO is apparently supposed to undo catchers, which wouldn't happen
    if it becomes a function call...  Is this analysis correct?  If so,
    then perhaps the standard deserves something a little stronger than
    the phrase "can break up catchers if necessary to get to the target"
    (middle of p. 131), which leaves me wondering what else GOs are supposed
    to do to get to those elusive targets...

Most people implement non-local GO in terms of THROW and local GO.

(tagbody (foo #'(lambda () (go a)))
         (baz)
       a (bar))
==>
(tagbody (case (catch g0001
		 (foo #'(lambda () (throw g0001 1)))
		 2)
	   (1 (go a))
	   (2 (baz)))
       a (bar))
or
(tagbody (catch g0001
	   (foo #'(lambda () (throw g0001 nil)))
	   (go g0002))
         (go a)
   g0002 (baz)
       a (bar))

where g0001 is bound to something dynamically unique (using
a gensym constant here won't work, you should easily be able
to construct a counterexample using recursive functions).

Regardless of your exact implementation, I think you'll find that cases
exist in which only an implementation of GO that uses THROW will work.