On Dec 1, 2010, at 9:52 AM, Duncan Sands wrote:> Hi Bill, > >> General Model >> ============>> >> The unwind edge from an invoke instruction jumps to a landing pad. That landing pad contains code which performs optional cleanups, and then determines which catch handler to call (if any). If no catch handlers are applicable, the exception resumes propagation either to the next enclosing region or out of the function. > > I was immediately struck by the fact that you describe cleanups as being run > before dispatching to handlers. In Ada handlers are run first and any cleanups > are run afterwards. As far as I know it is exactly the same in C++. Take your > example. I rewrite it with more explicit scopes: > > void bar() { > try { > foo(); > { // new scope > A a; > foo(); > { // new scope > ... etc... > } // end scope > } // end scope > } catch (int i) { > ... etc ... > } > > Here cleanups for "a", "b" etc are only run before the handlers are executed > because they are in inner scopes, and so are cleaned by unwinding before the > "try" scope is reached.I don't understand what you're trying to say here. I looked at the assembly for your first bar() function and it's exactly the same as would be emitted for one without the new scopes. Indeed, it's semantically identical. What do you mean by "before the try scope is reached"? If an exception is thrown by something in a nested scope, any variables live at that point must have their cleanups called before exiting the try block. And that occurs before the catch handlers are called.> Consider the following example instead: > > void bar() { > try { > A a; > foo(); > } catch (int i) { > ... etc ... > } > > If you check the assembler you will see that the destructor for "a" is run > before branching to the handler. >Correct. How is this a contradiction of what I wrote? I'm confused. -bw -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://lists.llvm.org/pipermail/llvm-dev/attachments/20101201/e1f5115d/attachment.html>
Hi Bill, ...> I don't understand what you're trying to say here. I looked at the assembly for > your first bar() function and it's exactly the same as would be emitted for one > without the new scopes. Indeed, it's semantically identical. What do you mean by > "before the try scope is reached"? If an exception is thrown by something in a > nested scope, any variables live at that point must have their cleanups called > before exiting the try block. And that occurs before the catch handlers are called. > >> Consider the following example instead: >> >> void bar() { >> try { >> A a; >> foo(); >> } catch (int i) { >> ... etc ... >> } >> >> If you check the assembler you will see that the destructor for "a" is run >> before branching to the handler. >> > Correct. How is this a contradiction of what I wrote? I'm confused.I got myself confused. Indeed it seems that C++ behaves the way you describe. However in Ada it is the other way round: cleanups are run after handlers. For example in Ada it would be possible to use the variable "a" inside one of the handlers, so it had better not be destructed before the handler runs. Thus it is important not to bake "cleanups run before handlers" into your proposal, since it is C++ specific. That said, as far as I can tell you didn't bake it in. Ciao, Duncan.
On Dec 1, 2010, at 11:42 AM, Duncan Sands wrote:> I got myself confused. Indeed it seems that C++ behaves the way you describe. > However in Ada it is the other way round: cleanups are run after handlers. For > example in Ada it would be possible to use the variable "a" inside one of the > handlers, so it had better not be destructed before the handler runs. Thus it > is important not to bake "cleanups run before handlers" into your proposal, > since it is C++ specific. That said, as far as I can tell you didn't bake it > in. >Ah! That explains it. :) Yes, they aren't baked in. You may run the cleanups whenever you wish. Or indeed not at all if you desire. :) -bw -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://lists.llvm.org/pipermail/llvm-dev/attachments/20101201/0146ef68/attachment.html>