It works just fine. Unwinding comes for free.
The entire condition system can be implemented safely using
return-from and
block. Other interesting special operators related to this are:
tagbody and
go,
throw and
catch, and finally
unwind-protect.
In practice, most condition systems actually are implemented only using the mentioned special forms and a few macros. It's also possible to implement some of those special operators as macros using other control-flow-related special operators, however for efficiency reasons, they are all considered special operators (for example, a
GO can be implemented as a jump in assembly most of the time, but a
THROW will cause a real exception which will cause stack unwinding until the
CATCH.
THROW is also slightly more expensive than
RETURN-FROM as
RETURN-FROM is local, while
THROW doesn't have to be).
If you're curious how the condition system is (or can be, in some other implementations) implemented only using these special operators, I suggest you look at SBCL's source code or read KMP's proof of concept implementation.
If you're curious how some of those operators are equivalent and how they can be metacircularily implemented within each other, read:
http://home.pipeline.com/~hbaker1/MetaCircular.ps.gz
If you have issues with the semantics, read the Hyperspec and experiment in your favorite implementation (also read its source, if it's an open source one).
I have Emacs+SLIME installed, the Hyperspec is only a key chord away (for any form, C-c C-d h) and implementation's source code is also just a key chord away (M-.), so learning about semantics or implementation details is very easy.