protected override IStatement ConvertFor(IForStatement ifs) { IExpression sizeExpr = Recognizer.LoopSizeExpression(ifs); if (sizeExpr is ILiteralExpression) { int size = (int)((ILiteralExpression)sizeExpr).Value; if (size < 20) { ConditionBinding binding = GetInitializerBinding(ifs); if (binding.rhs is ILiteralExpression) { int start = (int)((ILiteralExpression)binding.rhs).Value; for (int i = start; i < size; i++) { iterationContext.Add(new ConditionBinding(binding.lhs, Builder.LiteralExpr(i))); IBlockStatement body = ConvertBlock(ifs.Body); context.AddStatementsBeforeCurrent(body.Statements); iterationContext.RemoveAt(iterationContext.Count - 1); } return(null); } } } return(base.ConvertFor(ifs)); }
public override IBlockStatement Rewrite(IBlockStatement block) { while (true) { var specializedNestedType = this.type as ISpecializedNestedTypeDefinition; if (specializedNestedType != null) { this.type = specializedNestedType.ContainingTypeDefinition; //Carry on. At some point, the container must be a generic type instance. } else { var genInstance = this.type as IGenericTypeInstance; if (genInstance != null) { var argEnum = genInstance.GenericArguments.GetEnumerator(); var parEnum = genInstance.GenericType.ResolvedType.GenericParameters.GetEnumerator(); while (argEnum.MoveNext() && parEnum.MoveNext()) { this.genericArgumentsMap.Add(parEnum.Current.InternedKey, argEnum.Current); } return(base.Rewrite(block)); } else { Contract.Assume(false); //specialized methods should come either from specialized nested types, or from generic types intances. return(block); } } } }
public override void TraverseChildren(IBlockStatement block) { Contract.Assume(block is BlockStatement); var mutableBlock = (BlockStatement)block; this.Traverse(mutableBlock.Statements); foreach (var pair in this.declaringBlockMap) { if (pair.Value != mutableBlock) { continue; } var boundExpr = this.closureFieldToLocalOrParameterMap[pair.Key] as BoundExpression; if (boundExpr == null) { Contract.Assume(false); continue; } var local = boundExpr.Definition as ILocalDefinition; if (local == null) { Contract.Assume(false); continue; } var localDecl = new LocalDeclarationStatement() { LocalVariable = local }; mutableBlock.Statements.Insert(0, localDecl); } }
public override void TraverseChildren(IBlockStatement block) { this.Traverse(block.Statements); BasicBlock b = (BasicBlock)block; this.Traverse(b); }
public override void TraverseChildren(IBlockStatement block) { var savedCurrentBlock = this.currentBlock; var bb = (BasicBlock)block; this.currentBlock = bb; while (true) { var n = bb.Statements.Count; if (n == 0) { break; } for (int i = 0; i < n - 1; i++) { this.Traverse(bb.Statements[i]); } var bbb = bb.Statements[n - 1] as BasicBlock; if (bbb == null || this.loopHeader == null) { this.Traverse(bb.Statements[n - 1]); break; } bb = bbb; } this.Traverse(this.currentBlock); this.currentBlock = savedCurrentBlock; }
//public override void Visit(ISourceMethodBody methodBody) { // var block = methodBody.Block as BlockStatement; // // TODO: Error if cast fails? // if (block != null) { // var remover = new AnonymousDelegateRemover(this.sink.host, this.PdbReader); // var newTypes = remover.RemoveAnonymousDelegates(methodBody.MethodDefinition, block); // } // base.Visit(methodBody); //} public override void TraverseChildren(IBlockStatement block) { foreach (var s in block.Statements) { this.Traverse(s); } }
/// <summary> /// Visits the specified block. /// </summary> /// <param name="block">The block.</param> public override void Visit(IBlockStatement block) { if (this.insertAssumeFalseAtLine != null) { uint startLine; uint endLine; GetLocationLineSpan(GetPrimarySourceLocationFrom(block.Locations), out startLine, out endLine); if (startLine <= this.insertAssumeFalseAtLine.Value && this.insertAssumeFalseAtLine.Value < endLine) { foreach (IStatement stmt in block.Statements) { GetLocationLineSpan(GetPrimarySourceLocationFrom(stmt.Locations), out startLine, out endLine); GetPrimarySourceLocationFrom(stmt.Locations); if (this.insertAssumeFalseAtLine.Value < endLine) { AssumeStatement assumeFalse = new AssumeStatement(); CompileTimeConstant constFalse = new CompileTimeConstant(); constFalse.Value = false; assumeFalse.Condition = constFalse; this.GetOrCreateStmtListForStmt(stmt).Add(assumeFalse); break; } } } } base.Visit(block); }
internal void processMethod(IMethodDeclaration method) { IMethodDeclaration methodDecl = translator.TranslateMethodDeclaration(method); if (!(methodDecl is IConstructorDeclaration)) { IBlockStatement body = methodDecl.Body as IBlockStatement; if (body != null) { mutators = new Dictionary <IExpression, List <IExpression> >(); reportedErrors = new Dictionary <IExpression, bool>(); processStatement(body); reportErrors(); foreach (IExpression expr in reportedErrors.Keys) { String obj = expr is IFieldReferenceExpression ? ((IFieldReferenceExpression)expr).Field.Name : expr is IVariableReferenceExpression ? ((IVariableReferenceExpression)expr).Variable.Resolve().Name : expr.ToString(); messages.Append("Object \"" + obj + "\" is updated in method " + GetMethodName(methodDecl) + " without marking as modified\n"); } } } }
public override bool Equals(object obj) { if (this == obj) { return(true); } IBlockStatement statement = obj as IBlockStatement; if (statement == null || Statements.Count != statement.Statements.Count) { return(false); } for (int i = 0; i < Statements.Count; i++) { if (!(Statements[i].Equals(statement.Statements[i]))) { return(false); } } return(true); }
private void parseBlockForEventCancellation(IBlockStatement block, out bool cancels) { PhoneNavigationCallsTraverser traverser = new PhoneNavigationCallsTraverser(host); traverser.Traverse(block); cancels = traverser.CancelsEvents; }
public override ITypeDeclaration Transform(ITypeDeclaration itd) { bool useJaggedSubarrayWithMarginal = (this.algorithmDefault is ExpectationPropagation); analysis = new VariableAnalysisTransform(useJaggedSubarrayWithMarginal); analysis.Context.InputAttributes = context.InputAttributes; analysis.Transform(itd); context.Results = analysis.Context.Results; var itdOut = base.Transform(itd); if (context.trackTransform) { IBlockStatement block = Builder.BlockStmt(); block.Statements.Add(Builder.CommentStmt("variablesOmittingVariableFactor:")); foreach (var ivd in analysis.variablesExcludingVariableFactor) { block.Statements.Add(Builder.CommentStmt(ivd.ToString())); } context.OutputAttributes.Add(itdOut, new DebugInfo() { Transform = this, Name = "analysis", Value = block }); } return(itdOut); }
public override void TraverseChildren(IBlockStatement block) { base.TraverseChildren(block); Contract.Assume(block is BlockStatement); var decompiledBlock = (BlockStatement)block; var statements = decompiledBlock.Statements; for (int i = 0; i < statements.Count-1; i++) { var switchInstruction = statements[i] as SwitchInstruction; if (switchInstruction == null) continue; SwitchStatement result = new SwitchStatement(); result.Expression = switchInstruction.switchExpression; statements[i] = result; for (int j = 0, n = switchInstruction.SwitchCases.Count; j < n; j++) { CompileTimeConstant caseLabel = new CompileTimeConstant() { Value = j, Type = this.host.PlatformType.SystemInt32 }; var gotoCaseBody = switchInstruction.SwitchCases[j]; Contract.Assume(gotoCaseBody != null); SwitchCase currentCase = new SwitchCase() { Expression = caseLabel }; result.Cases.Add(currentCase); if (j < n-1) { Contract.Assume(switchInstruction.SwitchCases[j+1] != null); if (gotoCaseBody.TargetStatement == switchInstruction.SwitchCases[j+1].TargetStatement) continue; } currentCase.Body.Add(gotoCaseBody); } if (i == statements.Count-1) return; Contract.Assert(i+1 <= statements.Count); var gotoStatement = statements[i+1] as IGotoStatement; if (gotoStatement != null) { SwitchCase defaultCase = new SwitchCase() { }; // Default case is represented by a dummy Expression. defaultCase.Body.Add(statements[i + 1]); statements.RemoveAt(i + 1); result.Cases.Add(defaultCase); } } }
public override void TraverseChildren(IBlockStatement block) { BasicBlock basicBlock = (BasicBlock)block; List <ILocalDefinition> /*?*/ localsInCurrentScope = basicBlock.LocalVariables; if (localsInCurrentScope != null) { this.AddDeclarationsWithInitialValues(localsInCurrentScope, basicBlock); List <IStatement> prelude = new List <IStatement>(localsInCurrentScope.Count); foreach (ILocalDefinition localDef in localsInCurrentScope) { if (this.declaredLocals.ContainsKey(localDef)) { continue; } LocalDeclarationStatement localDecl = new LocalDeclarationStatement(); localDecl.LocalVariable = localDef; prelude.Add(localDecl); } if (prelude.Count > 0) { basicBlock.Statements.InsertRange(0, prelude); //TODO: use pdb info to insert them in the same order they appear in the source } } this.Traverse(basicBlock.Statements); }
public override void TraverseChildren(IBlockStatement block) { IList <Tuple <IStatement, StaticURIMode, string> > staticNavStmts = new List <Tuple <IStatement, StaticURIMode, string> >(); IList <IStatement> nonStaticNavStmts = new List <IStatement>(); foreach (IStatement statement in block.Statements) { navCallFound = false; navCallIsStatic = false; navCallIsBack = false; this.Traverse(statement); if (navCallFound) { navCallers.Add(methodTraversed); if (navCallIsStatic) { staticNavStmts.Add(new Tuple <IStatement, StaticURIMode, string>(statement, currentStaticMode, unpurifiedFoundURI)); } else if (!navCallIsBack) { nonStaticNavStmts.Add(statement); } } } injectNavigationUpdateCode(block, staticNavStmts, nonStaticNavStmts); }
protected override async Task <ImmutableArray <CodeAction> > GetRefactoringsAsync( Document document, IParameterSymbol parameter, TMemberDeclarationSyntax memberDeclaration, IBlockStatement blockStatementOpt, CancellationToken cancellationToken) { // Only should provide null-checks for reference types and nullable types. if (!parameter.Type.IsReferenceType && !parameter.Type.IsNullable()) { return(ImmutableArray <CodeAction> .Empty); } var syntaxFacts = document.GetLanguageService <ISyntaxFactsService>(); var semanticModel = await document.GetSemanticModelAsync(cancellationToken).ConfigureAwait(false); // Look for an existing "if (p == null)" statement, or "p ?? throw" check. If we already // have one, we don't want to offer to generate a new null check. // // Note: we only check the top level statements of the block. I think that's sufficient // as this will catch the 90% case, while not being that bad an experience even when // people do strange things in their constructors. if (blockStatementOpt != null) { foreach (var statement in blockStatementOpt.Statements) { if (IsIfNullCheck(statement, parameter)) { return(ImmutableArray <CodeAction> .Empty); } if (ContainsNullCoalesceCheck( syntaxFacts, semanticModel, statement, parameter, cancellationToken)) { return(ImmutableArray <CodeAction> .Empty); } } } // Great. There was no null check. Offer to add one. var result = ArrayBuilder <CodeAction> .GetInstance(); result.Add(new MyCodeAction( FeaturesResources.Add_null_check, c => AddNullCheckAsync(document, parameter, memberDeclaration, blockStatementOpt, c))); // Also, if this was a string, offer to add the special checks to // string.IsNullOrEmpty and string.IsNullOrWhitespace. if (parameter.Type.SpecialType == SpecialType.System_String) { result.Add(new MyCodeAction( FeaturesResources.Add_string_IsNullOrEmpty_check, c => AddStringCheckAsync(document, parameter, memberDeclaration, blockStatementOpt, nameof(string.IsNullOrEmpty), c))); result.Add(new MyCodeAction( FeaturesResources.Add_string_IsNullOrWhiteSpace_check, c => AddStringCheckAsync(document, parameter, memberDeclaration, blockStatementOpt, nameof(string.IsNullOrWhiteSpace), c))); } return(result.ToImmutableAndFree()); }
public override void TraverseChildren(IBlockStatement block) { Contract.Assume(block is BlockStatement); var decompiledBlock = (BlockStatement)block; var statements = decompiledBlock.Statements; for (int i = 0; i < statements.Count-3; i++) { var gotoCondition = statements[i] as GotoStatement; if (gotoCondition == null) continue; var gotosThatTarget = this.gotosThatTarget[(uint)gotoCondition.TargetStatement.Label.UniqueKey]; Contract.Assume(gotosThatTarget != null && gotosThatTarget.Count >= 1); if (gotosThatTarget.Count != 1) continue; var conditionalGotoBody = LookForCondition(statements, i+1, gotoCondition.TargetStatement); if (conditionalGotoBody == null || !(conditionalGotoBody.FalseBranch is EmptyStatement)) continue; var gotoBody = conditionalGotoBody.TrueBranch as GotoStatement; if (gotoBody == null) continue; Contract.Assume(i < statements.Count-3); if (!IsOrContainsAsFirstStatement(statements[i+1], gotoBody.TargetStatement)) continue; gotosThatTarget.Remove(gotoCondition); gotosThatTarget = this.gotosThatTarget[(uint)gotoBody.TargetStatement.Label.UniqueKey]; Contract.Assume(gotosThatTarget != null && gotosThatTarget.Count >= 1); gotosThatTarget.Remove(gotoBody); var loopBody = ExtractBlock(statements, i+1, gotoCondition.TargetStatement); var whileLoop = new WhileDoStatement() { Body = loopBody, Condition = conditionalGotoBody.Condition }; Contract.Assume(i < statements.Count); statements[i] = whileLoop; } base.TraverseChildren(block); }
private void ProcessBlockStatement(IBlockStatement pStatement) { foreach (IStatement statement in pStatement.Statements) { ProcessStatement(statement); } }
public override void TraverseChildren(IBlockStatement blockStatement) { base.TraverseChildren(blockStatement); Contract.Assume(blockStatement is BlockStatement); var block = (BlockStatement)blockStatement; var statements = block.Statements; var n = statements.Count; for (int i = 0; i < n; i++) { var nestedBlock = statements[i] as BlockStatement; if (nestedBlock != null) { if (nestedBlock.Statements.Count == 1) { var decompiledBlock = nestedBlock as DecompiledBlock; if (decompiledBlock != null && decompiledBlock.IsLexicalScope) { continue; } if (nestedBlock.Statements[0] is ILocalDeclarationStatement) { continue; } statements[i] = nestedBlock.Statements[0]; } else if (n == 1) { block.Statements = nestedBlock.Statements; return; } } } }
public override ITypeDeclaration Transform(ITypeDeclaration itd) { analysis = new ChannelAnalysisTransform(); analysis.Context.InputAttributes = context.InputAttributes; analysis.Transform(itd); context.Results = analysis.Context.Results; var itdOut = base.Transform(itd); if (context.trackTransform && debug) { IBlockStatement block = Builder.BlockStmt(); foreach (var entry in analysis.usageInfo) { IVariableDeclaration ivd = entry.Key; var info = entry.Value; block.Statements.Add(Builder.CommentStmt(info.ToString())); } context.OutputAttributes.Add(itdOut, new DebugInfo() { Transform = this, Name = "analysis", Value = block }); } return(itdOut); }
public override ITypeDeclaration Transform(ITypeDeclaration itd) { var analysis = new LocalAnalysisTransform(this.compiler); analysis.Context.InputAttributes = context.InputAttributes; analysis.Transform(itd); context.Results = analysis.Context.Results; if (!context.Results.IsSuccess) { Error("analysis failed"); return(itd); } this.localInfoOfStmt = analysis.localInfoOfStmt; var itdOut = base.Transform(itd); if (context.trackTransform && debug) { IBlockStatement block = Builder.BlockStmt(); foreach (var entry in analysis.localInfoOfStmt.Values.SelectMany(dict => dict)) { var expr = entry.Key; var info = entry.Value; block.Statements.Add(Builder.CommentStmt(expr.ToString() + " " + StringUtil.ToString(info))); } context.OutputAttributes.Add(itdOut, new DebugInfo() { Transform = this, Name = "analysis", Value = block }); } return(itdOut); }
public static void VisitBlockStatementChildren <TStatement>( IBlockStatement <TStatement> blockStatement, IGenericStatementVisitor visitor) where TStatement : IStatement { VisitCollection(blockStatement.Statements, visitor); }
public override void TraverseChildren(IBlockStatement block) { Contract.Assume(block is BlockStatement); Contract.Assume(this.gotosThatTarget != null); var b = (BlockStatement)block; for (int i = 0; i < b.Statements.Count; i++) { var label = b.Statements[i] as LabeledStatement; if (label != null) { var gotos = this.gotosThatTarget.Find((uint)label.Label.UniqueKey); if (gotos == null || gotos.Count == 0) { b.Statements.RemoveAt(i--); } } else { var gotoStatement = b.Statements[i] as GotoStatement; if (gotoStatement == null || gotoStatement.TargetStatement != this.targetLabel) { continue; } var gotos = this.gotosThatTarget.Find((uint)gotoStatement.TargetStatement.Label.UniqueKey); if (gotos != null) { gotos.Remove(gotoStatement); } b.Statements.RemoveAt(i--); } } this.Traverse(b.Statements); }
public override void VisitBlockStatement <TStatement>(IBlockStatement <TStatement> blockStatement) { Value = new Statement() { BlockStatement = new BlockStatementFactory(blockStatement).Value }; }
public static bool IsDeferringCtor(IMethodDefinition method, IBlockStatement body) { var fcc = new FindCtorCall(method.ContainingType); fcc.Traverse(body); return(fcc.isDeferringCtor); }
public override void TraverseChildren(IBlockStatement block) { BasicBlock blockStatement = (BasicBlock)block; List<IStatement> flatListOfStatements = new List<IStatement>(); this.Flatten(blockStatement, flatListOfStatements); blockStatement.Statements = flatListOfStatements; }
public override void TraverseChildren(IBlockStatement block) { BasicBlock blockStatement = (BasicBlock)block; List <IStatement> flatListOfStatements = new List <IStatement>(); this.Flatten(blockStatement, flatListOfStatements); blockStatement.Statements = flatListOfStatements; }
public override void Visit(IBlockStatement block) { if (Process(block)) { visitor.Visit(block); } base.Visit(block); }
private void parseBlockForNavigation(IBlockStatement block, out bool navigates, out ICollection <string> navTargets) { PhoneNavigationCallsTraverser traverser = new PhoneNavigationCallsTraverser(host); traverser.Traverse(block); navigates = traverser.CodeDoesNavigation; navTargets = traverser.NavigationTargets; }
internal static void WriteBlock(LanguageWriter w, IBlockStatement blockStatement) { if (blockStatement.Statements.Count == 0) { return; } WriteStatementCollection(w, blockStatement.Statements); }
public static IBlockStatement RemoveCachedDelegates(IMetadataHost host, IBlockStatement blockStatement, SourceMethodBody sourceMethodBody) { var finder = new FindAssignmentToCachedDelegateStaticFieldOrLocal(sourceMethodBody); finder.Traverse(blockStatement); if (finder.cachedDelegateFieldsOrLocals.Count == 0) return blockStatement; var mutator = new CachedDelegateRemover(host, finder.cachedDelegateFieldsOrLocals); return mutator.Visit(blockStatement); }
public override void TraverseChildren(IBlockStatement block) { base.TraverseChildren(block); BasicBlock bb = block as BasicBlock; if (bb != null) FindPattern(bb.Statements); return; }
private IExpression /*?*/ GetMonitor(IBlockStatement block, ILocalDefinition local, out ILocalDefinition monitorVar) { Contract.Ensures(Contract.Result <IExpression>() == null || Contract.ValueAtReturn <ILocalDefinition>(out monitorVar) != null); monitorVar = null; Contract.Assume(block is BlockStatement); var decompiledBlock = (BlockStatement)block; var statements = decompiledBlock.Statements; var n = statements.Count; if (n < 3) { return(null); } var pushStatement = statements[0] as PushStatement; if (pushStatement == null) { return(null); } var exprStatement1 = statements[1] as ExpressionStatement; if (exprStatement1 == null) { return(null); } var assignment1 = exprStatement1.Expression as Assignment; if (assignment1 == null || !(assignment1.Source is IDupValue)) { return(null); } monitorVar = assignment1.Target.Definition as ILocalDefinition; if (monitorVar == null) { return(null); } var exprStatement2 = statements[2] as ExpressionStatement; if (exprStatement2 == null) { return(null); } var methodCall = exprStatement2.Expression as MethodCall; if (methodCall == null) { return(null); } if (methodCall.Arguments.Count != 2 || !(methodCall.Arguments[0] is IPopValue)) { return(null); } if (methodCall.MethodToCall.InternedKey != this.monitorEnter.InternedKey) { return(null); } return(pushStatement.ValueToPush); }
internal LocalRefVariableStatement(IVariableDeclaration decl, IExpression exp, IBlockStatement block) { this.decl = decl; this.var_type = decl.VariableType; this.var_name = decl.Name; this.exp = exp; this.block = block; this.labelname = null; }
public override void TraverseChildren(IBlockStatement block) { base.TraverseChildren(block); Contract.Assume(block is BlockStatement); var decompiledBlock = (BlockStatement)block; var statements = decompiledBlock.Statements; for (int i = 0; i < statements.Count - 1; i++) { var switchInstruction = statements[i] as SwitchInstruction; if (switchInstruction == null) { continue; } SwitchStatement result = new SwitchStatement(); result.Expression = switchInstruction.switchExpression; statements[i] = result; for (int j = 0, n = switchInstruction.SwitchCases.Count; j < n; j++) { CompileTimeConstant caseLabel = new CompileTimeConstant() { Value = j, Type = this.host.PlatformType.SystemInt32 }; var gotoCaseBody = switchInstruction.SwitchCases[j]; Contract.Assume(gotoCaseBody != null); SwitchCase currentCase = new SwitchCase() { Expression = caseLabel }; result.Cases.Add(currentCase); if (j < n - 1) { Contract.Assume(switchInstruction.SwitchCases[j + 1] != null); if (gotoCaseBody.TargetStatement == switchInstruction.SwitchCases[j + 1].TargetStatement) { continue; } } currentCase.Body.Add(gotoCaseBody); } if (i == statements.Count - 1) { return; } Contract.Assert(i + 1 <= statements.Count); var gotoStatement = statements[i + 1] as IGotoStatement; if (gotoStatement != null) { SwitchCase defaultCase = new SwitchCase() { }; // Default case is represented by a dummy Expression. defaultCase.Body.Add(statements[i + 1]); statements.RemoveAt(i + 1); result.Cases.Add(defaultCase); } } }
public override void VisitBlockStatement(IBlockStatement operation) { foreach (var local in operation.Locals) { // empty loop body, just want to make sure it won't crash. } base.VisitBlockStatement(operation); }
public override void TraverseChildren(IBlockStatement block) { BasicBlock bb = block as BasicBlock; if (bb != null) { FindPattern(bb.Statements); if (bb.Statements.Count > 0) { BasicBlock nbb = bb.Statements[bb.Statements.Count-1] as BasicBlock; if (nbb != null) this.Traverse(nbb); } } }
public override void TraverseChildren(IBlockStatement block) { BasicBlock/*?*/ b = (BasicBlock)block; var blockTreeAsList = new List<BasicBlock>(); for (; ; ) { blockTreeAsList.Add(b); var i = b.Statements.Count-1; if (i <= 0) break; b = b.Statements[i] as BasicBlock; if (b == null) break; } for (int i = blockTreeAsList.Count-1; i >= 0; i--) this.Traverse(blockTreeAsList[i]); }
/// <summary> /// Given a method definition and a block of statements that represents the Block property of the body of the method, /// returns a SourceMethod with a body that no longer has any yield statements or anonymous delegate expressions. /// The given block of statements is mutated in place. /// </summary> public SourceMethodBody GetNormalizedSourceMethodBodyFor(IMethodDefinition method, IBlockStatement body) { var finder = new ClosureFinder(method, this.host); finder.Traverse(body); var privateHelperTypes = new List<ITypeDefinition>(); if (finder.foundYield) { this.isIteratorBody = true; body = this.GetNormalizedIteratorBody(body, method, privateHelperTypes); } SourceMethodBody result = new SourceMethodBody(this.host, this.sourceLocationProvider); result.Block = body; result.MethodDefinition = method; result.IsNormalized = true; result.LocalsAreZeroed = true; result.PrivateHelperTypes = privateHelperTypes; return result; }
public override void TraverseChildren(IBlockStatement block) { BasicBlock basicBlock = (BasicBlock)block; List<ILocalDefinition>/*?*/ localsInCurrentScope = basicBlock.LocalVariables; if (localsInCurrentScope != null) { this.AddDeclarationsWithInitialValues(localsInCurrentScope, basicBlock); List<IStatement> prelude = new List<IStatement>(localsInCurrentScope.Count); foreach (ILocalDefinition localDef in localsInCurrentScope) { if (this.declaredLocals.ContainsKey(localDef)) continue; LocalDeclarationStatement localDecl = new LocalDeclarationStatement(); localDecl.LocalVariable = localDef; prelude.Add(localDecl); } if (prelude.Count > 0) basicBlock.Statements.InsertRange(0, prelude); //TODO: use pdb info to insert them in the same order they appear in the source } this.Traverse(basicBlock.Statements); }
public override void TraverseChildren(IBlockStatement block) { base.TraverseChildren(block); Contract.Assume(block is BlockStatement); var decompiledBlock = (BlockStatement)block; var statements = decompiledBlock.Statements; for (int i = 0; i < statements.Count-1; i++) { //TODO: need to deal with patterns where the decl and the assignment are separated. var loclDecl = statements[i] as LocalDeclarationStatement; if (loclDecl == null) continue; var local = loclDecl.LocalVariable; if (local.Type.TypeCode != PrimitiveTypeCode.Boolean) continue; //if (this.sourceLocationProvider != null) { // bool isCompilerGenerated; // var sourceName = this.sourceLocationProvider.GetSourceNameFor(local, out isCompilerGenerated); // if (!isCompilerGenerated) continue; //} var tryFinallyStatement = statements[i+1] as TryCatchFinallyStatement; if (tryFinallyStatement == null) continue; if (tryFinallyStatement.FinallyBody == null || tryFinallyStatement.CatchClauses.Count > 0 || tryFinallyStatement.FaultBody != null) continue; ILocalDefinition monitorVar; var monitorObject = this.GetMonitor(tryFinallyStatement.TryBody, local, out monitorVar); if (monitorObject == null) continue; if (!this.FinallyBodyCallsMonitorExit(tryFinallyStatement.FinallyBody, local, monitorVar)) continue; this.numberOfAssignmentsToLocal[local]-=2; this.numberOfReferencesToLocal[local]-=2; this.numberOfAssignmentsToLocal[monitorVar]--; this.numberOfReferencesToLocal[monitorVar]--; var tryStatements = ((BlockStatement)tryFinallyStatement.TryBody).Statements; tryStatements.RemoveRange(0, 3); var body = new BlockStatement() { Statements = tryStatements }; var lockStatement = new LockStatement() { Guard = monitorObject, Body = body, Locations = tryFinallyStatement.Locations }; statements[i] = lockStatement; statements.RemoveAt(i+1); if (this.numberOfAssignmentsToLocal[monitorVar] == 0) { for (int j = 0; j < statements.Count; j++) { var ldecl = statements[j] as LocalDeclarationStatement; if (ldecl == null) continue; if (ldecl.LocalVariable != monitorVar) continue; statements.RemoveAt(j); break; } } } }
public static IBlockStatement GetRidOfStack(SourceMethodBody methodBody, IBlockStatement block) { var me = new Unstacker(methodBody); var result = me.Rewrite(block); var stmts = new List<IStatement>(); foreach (var loc in me.createdLocals.Values) { var decl = new LocalDeclarationStatement() { InitialValue = null, LocalVariable = loc, }; stmts.Add(decl); } stmts.AddRange(result.Statements); var newBlock = new BlockStatement() { Statements = stmts, Locations = new List<ILocation>(result.Locations), }; return newBlock; }
public override void TraverseChildren(IBlockStatement blockStatement) { base.TraverseChildren(blockStatement); Contract.Assume(blockStatement is BlockStatement); var block = (BlockStatement)blockStatement; var statements = block.Statements; var n = statements.Count; for (int i = 0; i < n; i++) { var nestedBlock = statements[i] as BlockStatement; if (nestedBlock != null) { if (nestedBlock.Statements.Count == 1) { var decompiledBlock = nestedBlock as DecompiledBlock; if (decompiledBlock != null && decompiledBlock.IsLexicalScope) continue; if (nestedBlock.Statements[0] is ILocalDeclarationStatement) continue; statements[i] = nestedBlock.Statements[0]; } else if (n == 1) { block.Statements = nestedBlock.Statements; return; } } } }
public override void TraverseChildren(IBlockStatement blockStatement) { base.TraverseChildren(blockStatement); Contract.Assume(blockStatement is BlockStatement); var block = (BlockStatement)blockStatement; int numberOfNonLexicalBlocks = 0; int numberOfNonLexicalStatements = 0; foreach (var statement in block.Statements) { var nestedBlock = statement as DecompiledBlock; if (nestedBlock == null) continue; if (nestedBlock.IsLexicalScope) continue; numberOfNonLexicalBlocks++; numberOfNonLexicalStatements += nestedBlock.Statements.Count; } if (numberOfNonLexicalBlocks == 0) return; var flattenedList = new List<IStatement>(block.Statements.Count-numberOfNonLexicalBlocks+numberOfNonLexicalStatements); foreach (var statement in block.Statements) { var nestedBlock = statement as DecompiledBlock; if (nestedBlock == null || nestedBlock.IsLexicalScope) flattenedList.Add(statement); else flattenedList.AddRange(nestedBlock.Statements); } block.Statements = flattenedList; }
public override void TraverseChildren(IBlockStatement block) { Contract.Assume(block is BlockStatement); var decompiledBlock = (BlockStatement)block; var statements = decompiledBlock.Statements; for (int i = 0; i < statements.Count-1; i++) { IStatement initializer = null; var initializerAssignStat = statements[i] as IExpressionStatement; if (initializerAssignStat != null) { if (!(initializerAssignStat.Expression is IAssignment)) continue; initializer = initializerAssignStat; i++; } else { var initialDecl = statements[i] as ILocalDeclarationStatement; if (initialDecl == null || initialDecl.InitialValue == null) continue; initializer = initialDecl; i++; } var whileLoop = statements[i] as IWhileDoStatement; if (whileLoop == null) continue; var loopBody = whileLoop.Body as BlockStatement; if (loopBody == null) continue; var incrementer = FindLastStatement(loopBody) as IExpressionStatement; if (incrementer == null) continue; var incrementAssignment = incrementer.Expression as IAssignment; if (incrementAssignment == null || !(incrementAssignment.Source is IAddition || incrementAssignment.Source is ISubtraction)) continue; var forLoop = new ForStatement() { Condition = whileLoop.Condition, Body = loopBody }; if (initializer != null) { statements.RemoveAt(--i); forLoop.InitStatements.Add(initializer); } RemoveLastStatement(loopBody, incrementer); forLoop.IncrementStatements.Add(incrementer); statements[i] = forLoop; } base.TraverseChildren(block); }
/// <summary> /// For an iterator method, find the closure class' MoveNext method and return its body. /// </summary> /// <param name="iteratorIL">The body of the iterator method, decompiled from the ILs of the iterator body.</param> /// <returns>Dummy.MethodBody if <paramref name="iteratorIL"/> does not fit into the code pattern of an iterator method, /// or the body of the MoveNext method of the corresponding closure class if it does. /// </returns> IMethodBody FindClosureMoveNext(IBlockStatement/*!*/ iteratorIL) { foreach (var statement in iteratorIL.Statements) { ICreateObjectInstance createObjectInstance = GetICreateObjectInstance(statement); if (createObjectInstance == null) { // If the first statement in the method body is not the creation of iterator closure, return a dummy. // Possible corner case not handled: a local is used to hold the constant value for the initial state of the closure. return Dummy.MethodBody; } ITypeReference closureType/*?*/ = createObjectInstance.MethodToCall.ContainingType; ITypeReference unspecializedClosureType = GetUnspecializedType(closureType); if (!AttributeHelper.Contains(unspecializedClosureType.Attributes, closureType.PlatformType.SystemRuntimeCompilerServicesCompilerGeneratedAttribute)) return Dummy.MethodBody; INestedTypeReference closureTypeAsNestedTypeReference = unspecializedClosureType as INestedTypeReference; if (closureTypeAsNestedTypeReference == null) return Dummy.MethodBody; ITypeReference unspecializedClosureContainingType = GetUnspecializedType(closureTypeAsNestedTypeReference.ContainingType); if (closureType != null && TypeHelper.TypesAreEquivalent(this.ilMethodBody.MethodDefinition.ContainingTypeDefinition, unspecializedClosureContainingType)) { IName MoveNextName = this.nameTable.GetNameFor("MoveNext"); foreach (ITypeDefinitionMember member in closureType.ResolvedType.GetMembersNamed(MoveNextName, false)) { IMethodDefinition moveNext = member as IMethodDefinition; if (moveNext != null) { ISpecializedMethodDefinition moveNextGeneric = moveNext as ISpecializedMethodDefinition; if (moveNextGeneric != null) moveNext = moveNextGeneric.UnspecializedVersion.ResolvedMethod; var body = moveNext.Body; var sourceBody = body as SourceMethodBody; //it may already have been decompiled. if (sourceBody != null) body = sourceBody.ilMethodBody; //TODO: it would be nice to avoid decompiling it again return body; } } } return Dummy.MethodBody; } return Dummy.MethodBody; }
private IBlockStatement DecompileMoveNext(IBlockStatement block) { return new MoveNextDecompiler(this.ilMethodBody.MethodDefinition.ContainingTypeDefinition, this.host).Decompile((BlockStatement)block); }
private IBlockStatement AddLocalDeclarationIfNecessary(IBlockStatement block) { return new ClosureLocalVariableDeclarationAdder(this).Visit(block); }
public override void TraverseChildren(IBlockStatement block) { var saved = this.currentBlock; this.currentBlock = block; base.TraverseChildren(block); this.currentBlock = saved; }
public override void TraverseChildren(IBlockExpression blockExpression) { var saved = this.currentBlock; this.currentBlock = blockExpression.BlockStatement; base.TraverseChildren(blockExpression.BlockStatement); this.Traverse(blockExpression.Expression); this.currentBlock = saved; }
/// <summary> /// /// </summary> public AnonymousDelegate() { this.body = CodeDummy.Block; this.callingConvention = CallingConvention.Default; this.parameters = new List<IParameterDefinition>(); this.returnType = Dummy.TypeReference; this.returnValueCustomModifiers = new List<ICustomModifier>(); this.returnValueIsByRef = false; }
public virtual void onASTElement(IBlockStatement block) { }
/// <summary> /// /// </summary> /// <param name="blockStatement"></param> public BlockStatement(IBlockStatement blockStatement) : base(blockStatement) { this.statements = new List<IStatement>(blockStatement.Statements); this.useCheckedArithmetic = blockStatement.UseCheckedArithmetic; }
private bool TryFindAssignmentExpression( IBlockStatement containingBlock, IIfStatement ifOperation, ISymbol localOrParameter, out IExpressionStatement expressionStatement, out IAssignmentExpression assignmentExpression) { var ifOperationIndex = containingBlock.Statements.IndexOf(ifOperation); // walk forward until we find an assignment of this local/parameter into // something else. for (var i = ifOperationIndex + 1; i < containingBlock.Statements.Length; i++) { expressionStatement = containingBlock.Statements[i] as IExpressionStatement; if (expressionStatement == null) { continue; } assignmentExpression = expressionStatement.Expression as IAssignmentExpression; if (assignmentExpression == null) { continue; } if (!TryGetLocalOrParameterSymbol(assignmentExpression.Value, out var assignmentValue)) { continue; } if (!Equals(localOrParameter, assignmentValue)) { continue; } return true; } expressionStatement = null; assignmentExpression = null; return false; }
public virtual void VisitBlockStatement(IBlockStatement operation) { DefaultVisit(operation); }
/// <summary> /// /// </summary> /// <param name="blockExpression"></param> public BlockExpression(IBlockExpression blockExpression) : base(blockExpression) { this.blockStatement = blockExpression.BlockStatement; this.expression = blockExpression.Expression; }
/// <summary> /// /// </summary> public BlockExpression() { this.blockStatement = CodeDummy.Block; this.expression = CodeDummy.Expression; }
/// <summary> /// /// </summary> /// <param name="anonymousDelegate"></param> public AnonymousDelegate(IAnonymousDelegate anonymousDelegate) : base(anonymousDelegate) { this.body = anonymousDelegate.Body; this.callingConvention = anonymousDelegate.CallingConvention; this.parameters = new List<IParameterDefinition>(anonymousDelegate.Parameters); this.returnType = anonymousDelegate.ReturnType; this.returnValueCustomModifiers = new List<ICustomModifier>(anonymousDelegate.ReturnValueCustomModifiers); this.returnValueIsByRef = anonymousDelegate.ReturnValueIsByRef; }
/// <summary> /// Constructs a pair from the arguments. /// </summary> public MethodContractAndMethodBody(IMethodContract/*?*/ methodContract, IBlockStatement/*?*/ blockStatement) { this.methodContract = methodContract; this.blockStatement = blockStatement; }
public override void TraverseChildren(IBlockStatement block) { base.TraverseChildren(block); Contract.Assume(block is DecompiledBlock); var b = (DecompiledBlock)block; int i = 0; int n = b.ContainedBlocks.Count; for (int j = 0, m = b.Statements.Count; j < m; j++) { var nb = b.Statements[j] as DecompiledBlock; if (nb == null) continue; while (i < n) { var bb = b.ContainedBlocks[i++]; if (DecompiledBlock.GetStartOffset(bb) == nb.StartOffset) continue; if (DecompiledBlock.GetStartOffset(bb) >= nb.EndOffset) break; } } while (i < n) { var bb = b.ContainedBlocks[i++]; this.ParseBasicBlock(b.Statements, bb); } }