public IEnumerable <IInstruction> EndTry(bool generateExit, out IInstruction jump) { var code = new AbcCode(_abc); jump = generateExit ? code.Goto() //exit from protected region : null; return(code); }
public IEnumerable <IInstruction> EndCatch(ISehHandlerBlock handlerBlock, bool isLast, bool generateExit, out IInstruction jump) { var ci = handlerBlock.GetCatchInfo(); jump = null; var code = new AbcCode(_abc); if (PopCatchScope) { code.PopScope(); //pops catch scope } //we now no need in exception variable KillExceptionVariable(code, ci); //NOTE: no need to generate exit jump for last catch block if (generateExit && !isLast) { jump = code.Goto(); } return(code); }
private IEnumerable <IInstruction> BeginFinally(ISehHandlerBlock block, bool fault) { var e = new AbcExceptionHandler(); _body.Exceptions.Add(e); e.To = -1; e.Target = -1; var fi = new FinallyInfo { IsFault = fault }; block.Tag = new SehHandlerInfo { FinallyInfo = fi }; _resolver.Add(block.Owner, new ExceptionFrom(e), null); var code = new AbcCode(_abc); if (!fault) { //Reset rethrow flag fi.RethrowFlagVariable = NewTempVar(true); _initializableTempVars.Add(new TempVar(fi.RethrowFlagVariable, new Instruction(InstructionCode.Pushfalse))); code.PushNativeBool(false); // Trying to fix IVDiffGramTest. Coercing to any type does not help. The test failed with error: // The Dark Side clouds everything. Impossible to see, the future is. (c) Yoda // code.CoerceAnyType(); code.SetLocal(fi.RethrowFlagVariable); } //Add goto finally body var gotoBody = code.Goto(); _resolver.Add(gotoBody, new ExceptionTo(e)); //NOTE: Insert empty handler to catch unhandled or rethrown exception //begin catch BeginCatch(block, code, e, ref fi.ExceptionVariable, false, false); var end = (Instruction)code[code.Count - 1]; if (!fault) { //Set rethrow flag to true to rethrow exception code.PushNativeBool(true); // Trying to fix IVDiffGramTest. Coercing to any type does not help. The test failed with error: // The Dark Side clouds everything. Impossible to see, the future is. (c) Yoda // code.CoerceAnyType(); end = code.SetLocal(fi.RethrowFlagVariable); } if (PopCatchScope) { end = code.PopScope(); //pops catch scope } //end of catch gotoBody.GotoNext(end); return(code); }
void RouteException(AbcCode code, ISehHandlerBlock block, int var) { var exceptionType = block.ExceptionType; if (block.PrevHandler == null) { //if err is AVM error then we translate it to System.Exception. //code.GetLocal(var); //code.As(AvmTypeCode.Error); //code.PushNull(); //var ifNotError = code.IfEquals(); code.GetLocal(var); code.As(SystemTypes.Exception, true); code.PushNull(); var ifExc = code.IfNotEquals(); code.GetLocal(var); code.As(AvmTypeCode.Error); code.PushNull(); var ifNotError = code.IfEquals(); CallToException(code, var); code.CoerceAnyType(); code.SetLocal(var); //check my exception var labelNotError = code.Label(); ifExc.BranchTarget = labelNotError; ifNotError.BranchTarget = labelNotError; } code.GetLocal(var); var handlerInfo = (SehHandlerInfo)block.Tag; handlerInfo.CheckExceptionLabel = code.Label(); //NOTE: Exception on stack can be routed from previous handlers code.SetLocal(var); code.GetLocal(var); code.As(exceptionType, true); code.PushNull(); var ifMyException = code.IfNotEquals(); //Routing to another exception handler or rethrow //Instruction routing = Label(); if (block.NextHandler == null) { code.GetLocal(var); code.Throw(); } else { code.GetLocal(var); handlerInfo.JumpToNextHandler = code.Goto(); } //Normal Execution: Prepare stack for handler var normal = code.Label(); ifMyException.BranchTarget = normal; code.GetLocal(var); code.Coerce(exceptionType, true); //21 instructions for first handler //11 instructions for other handlers }