# HG changeset patch # User Christian Kamm # Date 1238264213 -3600 # Node ID 7d28dcbff23e5ab6fc31fd8a7b44c09a2e5ef52b # Parent c6d6a68bb5db3845dc3199bad87b972bfe580173 Reenable error for gotos into or out of finally blocks. diff -r c6d6a68bb5db -r 7d28dcbff23e gen/asmstmt.cpp --- a/gen/asmstmt.cpp Sat Mar 28 14:39:16 2009 +0100 +++ b/gen/asmstmt.cpp Sat Mar 28 19:16:53 2009 +0100 @@ -772,7 +772,7 @@ sw->addCase(llvm::ConstantInt::get(llvm::IntegerType::get(32), it->second), casebb); p->scope() = IRScope(casebb,bb); - DtoGoto(loc, it->first); + DtoGoto(loc, it->first, enclosingFinally); } p->scope() = IRScope(bb,oldend); diff -r c6d6a68bb5db -r 7d28dcbff23e gen/llvmhelpers.cpp --- a/gen/llvmhelpers.cpp Sat Mar 28 14:39:16 2009 +0100 +++ b/gen/llvmhelpers.cpp Sat Mar 28 19:16:53 2009 +0100 @@ -172,7 +172,7 @@ /*//////////////////////////////////////////////////////////////////////////////////////// // GOTO HELPER ////////////////////////////////////////////////////////////////////////////////////////*/ -void DtoGoto(Loc loc, Identifier* target) +void DtoGoto(Loc loc, Identifier* target, TryFinallyStatement* sourceFinally) { assert(!gIR->scopereturned()); @@ -199,11 +199,10 @@ // goto into finally blocks is forbidden by the spec // but should work fine - /* - if(lblstmt->tf != sourcetf) { - error(loc, "spec disallows goto into finally block"); + if(lblstmt->enclosingFinally != sourceFinally) { + error(loc, "spec disallows goto into or out of finally block"); fatal(); - }*/ + } llvm::BranchInst::Create(targetBB, gIR->scopebb()); } diff -r c6d6a68bb5db -r 7d28dcbff23e gen/llvmhelpers.h --- a/gen/llvmhelpers.h Sat Mar 28 14:39:16 2009 +0100 +++ b/gen/llvmhelpers.h Sat Mar 28 19:16:53 2009 +0100 @@ -45,8 +45,10 @@ // return the LabelStatement from the current function with the given identifier or NULL if not found LabelStatement* DtoLabelStatement(Identifier* ident); -// emit goto -void DtoGoto(Loc loc, Identifier* target); + +/// emits goto to LabelStatement with the target identifier +/// the sourceFinally is only used for error checking +void DtoGoto(Loc loc, Identifier* target, TryFinallyStatement* sourceFinally); // Generates IR for enclosing handlers between the current state and // the scope created by the 'target' statement. diff -r c6d6a68bb5db -r 7d28dcbff23e gen/statements.cpp --- a/gen/statements.cpp Sat Mar 28 14:39:16 2009 +0100 +++ b/gen/statements.cpp Sat Mar 28 19:16:53 2009 +0100 @@ -1288,7 +1288,7 @@ llvm::BasicBlock* oldend = gIR->scopeend(); llvm::BasicBlock* bb = llvm::BasicBlock::Create("aftergoto", p->topfunc(), oldend); - DtoGoto(loc, label->ident); + DtoGoto(loc, label->ident, enclosingFinally); p->scope() = IRScope(bb,oldend); }