Previous: Hooking into the stack unwinding, Up: Exception handling

6.11.7 Handler stack unwinding caveat

One important difference between Smalltalk and other languages is that when a handler is invoked, the stack is not unwound. The Smalltalk exception system is designed this way because it's rare to write code that could break because of this difference, and the #resume: feature doesn't make sense if the stack is unwound. It is easy enough to unwind a stack later, and is not so easy to wind it again if done too early.

For almost all applications, this will not matter, but it technically changes the semantics significantly so should be kept in mind. One important case in which it might matter is when using #ensure: blocks and exception handlers. For comparison, this Smalltalk code:

     | n |
     n := 42.
     [[self error: 'error'] ensure: [n := 24]]
         on: Error
         do: [:sig | n printNl. sig return].
     n printNl.

will put "42" followed by "24" on the transcript, because the n := 24 will not be executed until sig return is invoked, unwinding the stack. Similar Java code acts differently:

     int n = 42;
         try {throw new Exception ("42");}
         finally {n = 24;}
     catch (Exception e)
         System.out.println (n);
     System.out.println (n);

printing "24" twice, because the stack unwinds before executing the catch block.