Move some helper methods to Extensions

This commit is contained in:
Diego 2018-01-23 09:42:32 -08:00
Родитель fea4d87b29
Коммит fe0adfd0ed
3 изменённых файлов: 208 добавлений и 208 удалений

Просмотреть файл

@ -138,7 +138,7 @@ namespace ScopeProgramAnalysis
//var cfg = this.moveNextMethod.DoAnalysisPhases(host, this.GetMethodsToInline());
var cfg = this.interprocManager.GetCFG(processToAnalyze.MoveNextMethod);
PropagateExpressions(cfg, this.equalities);
cfg.PropagateExpressions(this.equalities);
// In general, the variable to bind is going to be pointsToEntry.ReturnVariable which is aliased with "$_temp_it" (myGetEnumResult)
SimplePointsToGraph calleePTG = InterproceduralManager.PTABindCallerCallee(ptgAfterEnum, new List<IVariable> { myGetEnumResult }, processToAnalyze.MoveNextMethod);
this.pointsToAnalyzer = new IteratorPointsToAnalysis(cfg, processToAnalyze.MoveNextMethod, calleePTG);
@ -264,38 +264,6 @@ namespace ScopeProgramAnalysis
return false;
}
#region Methods to Compute a sort of propagation of Equalities (should be moved to extensions or utils)
public static void PropagateExpressions(ControlFlowGraph cfg, IDictionary<IVariable, IExpression> equalities)
{
foreach (var node in cfg.ForwardOrder)
{
PropagateExpressions(node, equalities);
}
}
private static void PropagateExpressions(CFGNode node, IDictionary<IVariable, IExpression> equalities)
{
foreach (var instruction in node.Instructions)
{
PropagateExpressions(instruction, equalities);
}
}
private static void PropagateExpressions(Instruction instruction, IDictionary<IVariable, IExpression> equalities)
{
var definition = instruction as DefinitionInstruction;
if (definition != null && definition.HasResult)
{
var expr = definition.ToExpression().ReplaceVariables(equalities);
equalities.Add(definition.Result, expr);
}
}
#endregion
}
}

Просмотреть файл

@ -169,7 +169,7 @@ namespace ScopeProgramAnalysis
IteratorPointsToAnalysis calleePTA = new IteratorPointsToAnalysis(calleeCFG, callInfo.Callee, calleePTG);
IDictionary<IVariable, IExpression> equalities = new Dictionary<IVariable, IExpression>();
SongTaoDependencyAnalysis.PropagateExpressions(calleeCFG, equalities);
calleeCFG.PropagateExpressions(equalities);
var rangesAnalysis = new RangeAnalysis(calleeCFG);
rangesAnalysis.Analyze();

Просмотреть файл

@ -6,222 +6,254 @@ using System.Threading.Tasks;
using Backend;
using Backend.Analyses;
using Backend.Model;
using Backend.ThreeAddressCode.Expressions;
using Backend.ThreeAddressCode.Instructions;
using Backend.ThreeAddressCode.Values;
using Backend.Transformations;
using Backend.Utils;
using Microsoft.Cci;
namespace ScopeProgramAnalysis.Framework
{
public static class Extensions
{
public static ControlFlowGraph DoAnalysisPhases(this IMethodDefinition method, IMetadataHost host, ISourceLocationProvider locationProvider,
IEnumerable<IMethodReference> methodsToTryToInline = null)
{
AnalysisStats.extraAnalysisOverHead.Start();
var disassembler = new Disassembler(host, method, locationProvider);
public static class Extensions
{
public static ControlFlowGraph DoAnalysisPhases(this IMethodDefinition method, IMetadataHost host, ISourceLocationProvider locationProvider,
IEnumerable<IMethodReference> methodsToTryToInline = null)
{
AnalysisStats.extraAnalysisOverHead.Start();
var disassembler = new Disassembler(host, method, locationProvider);
var methodBody = disassembler.Execute();
var methodBody = disassembler.Execute();
MethodBodyProvider.Instance.AddBody(method, methodBody);
MethodBodyProvider.Instance.AddBody(method, methodBody);
if (methodsToTryToInline != null)
{
DoInlining(method, host, methodBody, locationProvider, methodsToTryToInline);
}
if (methodsToTryToInline != null)
{
DoInlining(method, host, methodBody, locationProvider, methodsToTryToInline);
}
var cfAnalysis = new ControlFlowAnalysis(methodBody);
//var cfg = cfAnalysis.GenerateExceptionalControlFlow();
var cfg = cfAnalysis.GenerateNormalControlFlow();
var cfAnalysis = new ControlFlowAnalysis(methodBody);
//var cfg = cfAnalysis.GenerateExceptionalControlFlow();
var cfg = cfAnalysis.GenerateNormalControlFlow();
var domAnalysis = new DominanceAnalysis(cfg);
domAnalysis.Analyze();
domAnalysis.GenerateDominanceTree();
var domAnalysis = new DominanceAnalysis(cfg);
domAnalysis.Analyze();
domAnalysis.GenerateDominanceTree();
var loopAnalysis = new NaturalLoopAnalysis(cfg);
loopAnalysis.Analyze();
var loopAnalysis = new NaturalLoopAnalysis(cfg);
loopAnalysis.Analyze();
var domFrontierAnalysis = new DominanceFrontierAnalysis(cfg);
domFrontierAnalysis.Analyze();
var domFrontierAnalysis = new DominanceFrontierAnalysis(cfg);
domFrontierAnalysis.Analyze();
var splitter = new WebAnalysis(cfg);
splitter.Analyze();
splitter.Transform();
var splitter = new WebAnalysis(cfg);
splitter.Analyze();
splitter.Transform();
methodBody.UpdateVariables();
methodBody.UpdateVariables();
var analysis = new TypeInferenceAnalysis(cfg);
analysis.Analyze();
var analysis = new TypeInferenceAnalysis(cfg);
analysis.Analyze();
var copyProgapagtion = new ForwardCopyPropagationAnalysis(cfg);
copyProgapagtion.Analyze();
copyProgapagtion.Transform(methodBody);
var copyProgapagtion = new ForwardCopyPropagationAnalysis(cfg);
copyProgapagtion.Analyze();
copyProgapagtion.Transform(methodBody);
//var backwardCopyProgapagtion = new BackwardCopyPropagationAnalysis(cfg);
//backwardCopyProgapagtion.Analyze();
//backwardCopyProgapagtion.Transform(methodBody);
//var backwardCopyProgapagtion = new BackwardCopyPropagationAnalysis(cfg);
//backwardCopyProgapagtion.Analyze();
//backwardCopyProgapagtion.Transform(methodBody);
var liveVariables = new LiveVariablesAnalysis(cfg);
var resultLiveVar = liveVariables.Analyze();
var liveVariables = new LiveVariablesAnalysis(cfg);
var resultLiveVar = liveVariables.Analyze();
var ssa = new StaticSingleAssignment(methodBody, cfg);
ssa.Transform();
ssa.Prune(liveVariables);
methodBody.UpdateVariables();
AnalysisStats.extraAnalysisOverHead.Stop();
return cfg;
}
var ssa = new StaticSingleAssignment(methodBody, cfg);
ssa.Transform();
ssa.Prune(liveVariables);
methodBody.UpdateVariables();
AnalysisStats.extraAnalysisOverHead.Stop();
return cfg;
}
public static IEnumerable<IMethodReference> GetMethodsInvoked(this IMethodDefinition method)
{
return MethodBodyProvider.Instance.GetBody(method).Instructions.OfType<MethodCallInstruction>().Select(ins => ins.Method);
}
public static IEnumerable<IMethodReference> GetMethodsInvoked(this IMethodDefinition method)
{
return MethodBodyProvider.Instance.GetBody(method).Instructions.OfType<MethodCallInstruction>().Select(ins => ins.Method);
}
private static void DoInlining(IMethodDefinition method, IMetadataHost host, MethodBody methodBody, ISourceLocationProvider sourceLocationProvider, IEnumerable<IMethodReference> methodsToTryToInline = null)
{
if (methodsToTryToInline == null)
methodsToTryToInline = new HashSet<IMethodReference>();
private static void DoInlining(IMethodDefinition method, IMetadataHost host, MethodBody methodBody, ISourceLocationProvider sourceLocationProvider, IEnumerable<IMethodReference> methodsToTryToInline = null)
{
if (methodsToTryToInline == null)
methodsToTryToInline = new HashSet<IMethodReference>();
var methodCalls = methodBody.Instructions.OfType<MethodCallInstruction>().Where(ins => methodsToTryToInline.Contains(ins.Method)).ToList();
foreach (var methodCall in methodCalls)
{
var callee = methodCall.Method.ResolvedMethod;
if (callee != null)
{
// var calleeCFG = DoAnalysisPhases(callee, host);
var disassemblerCallee = new Disassembler(host, callee, sourceLocationProvider);
var methodBodyCallee = disassemblerCallee.Execute();
methodBody.Inline(methodCall, methodBodyCallee);
}
}
var methodCalls = methodBody.Instructions.OfType<MethodCallInstruction>().Where(ins => methodsToTryToInline.Contains(ins.Method)).ToList();
foreach (var methodCall in methodCalls)
{
var callee = methodCall.Method.ResolvedMethod;
if (callee != null)
{
// var calleeCFG = DoAnalysisPhases(callee, host);
var disassemblerCallee = new Disassembler(host, callee, sourceLocationProvider);
var methodBodyCallee = disassemblerCallee.Execute();
methodBody.Inline(methodCall, methodBodyCallee);
}
}
methodBody.UpdateVariables();
methodBody.UpdateVariables();
}
}
public static string ContainingNamespace(this ITypeReference type)
{
if(type is INamedTypeDefinition)
return TypeHelper.GetDefiningNamespace((INamedTypeDefinition)type).ToString();
return String.Empty;
}
public static string ContainingNamespace(this ITypeReference type)
{
if (type is INamedTypeDefinition)
return TypeHelper.GetDefiningNamespace((INamedTypeDefinition)type).ToString();
return String.Empty;
}
public static string ContainingAssembly(this ITypeReference type)
{
return TypeHelper.GetDefiningUnitReference(type).Name.Value;
}
public static string ContainingAssembly(this ITypeReference type)
{
return TypeHelper.GetDefiningUnitReference(type).Name.Value;
}
public static bool IsConstructor(this IMethodReference method)
{
return method.Name.Value==".ctor";
}
public static bool IsConstructorCall(this Instruction ins)
{
if (ins is MethodCallInstruction)
{
var call = ins as MethodCallInstruction;
if (call.Method.IsConstructor())
{
return true;
}
}
return false;
}
public static bool IsConstructor(this IMethodReference method)
{
return method.Name.Value == ".ctor";
}
public static bool IsConstructorCall(this Instruction ins)
{
if (ins is MethodCallInstruction)
{
var call = ins as MethodCallInstruction;
if (call.Method.IsConstructor())
{
return true;
}
}
return false;
}
public static IMethodReference FindMethodImplementation(this ITypeReference receiverType, IMethodReference method)
{
var result = method;
public static IMethodReference FindMethodImplementation(this ITypeReference receiverType, IMethodReference method)
{
var result = method;
while (receiverType != null && !method.ContainingType.TypeEquals(receiverType))
{
var receiverTypeDef = receiverType.ResolvedType;
if (receiverTypeDef == null) break;
while (receiverType != null && !method.ContainingType.TypeEquals(receiverType))
{
var receiverTypeDef = receiverType.ResolvedType;
if (receiverTypeDef == null) break;
var matchingMethod = receiverTypeDef.Methods.SingleOrDefault(m => MemberHelper.SignaturesAreEqual(m, method));
var matchingMethod = receiverTypeDef.Methods.SingleOrDefault(m => MemberHelper.SignaturesAreEqual(m, method));
if (matchingMethod != null)
{
result = matchingMethod;
break;
}
else
{
receiverType = receiverTypeDef.BaseClasses.SingleOrDefault();
}
if (matchingMethod != null)
{
result = matchingMethod;
break;
}
else
{
receiverType = receiverTypeDef.BaseClasses.SingleOrDefault();
}
}
}
return result;
}
return result;
}
public static bool IsDelegateType(this ITypeReference type)
{
return type.ResolvedType != null && type.ResolvedType.IsDelegate;
}
public static bool IsDelegateType(this ITypeReference type)
{
return type.ResolvedType != null && type.ResolvedType.IsDelegate;
}
public static bool IsClassOrStruct(this ITypeReference type)
{
// BUG: type cannot be NULL!
if (type == null)
return true;
if (type.IsValueType)
{
if (type.ResolvedType.IsStruct)
{
switch (type.TypeCode)
{
case PrimitiveTypeCode.Boolean:
case PrimitiveTypeCode.Char:
case PrimitiveTypeCode.Int8:
case PrimitiveTypeCode.Float32:
case PrimitiveTypeCode.Float64:
case PrimitiveTypeCode.Int16:
case PrimitiveTypeCode.Int32:
case PrimitiveTypeCode.Int64:
case PrimitiveTypeCode.UInt8:
case PrimitiveTypeCode.UInt16:
case PrimitiveTypeCode.UInt32:
case PrimitiveTypeCode.UInt64:
case PrimitiveTypeCode.Void:
return false;
default:
return true;
}
}
}
return true;
}
public static bool IsClassOrStruct(this ITypeReference type)
{
// BUG: type cannot be NULL!
if (type == null)
return true;
if (type.IsValueType)
{
if (type.ResolvedType.IsStruct)
{
switch (type.TypeCode)
{
case PrimitiveTypeCode.Boolean:
case PrimitiveTypeCode.Char:
case PrimitiveTypeCode.Int8:
case PrimitiveTypeCode.Float32:
case PrimitiveTypeCode.Float64:
case PrimitiveTypeCode.Int16:
case PrimitiveTypeCode.Int32:
case PrimitiveTypeCode.Int64:
case PrimitiveTypeCode.UInt8:
case PrimitiveTypeCode.UInt16:
case PrimitiveTypeCode.UInt32:
case PrimitiveTypeCode.UInt64:
case PrimitiveTypeCode.Void:
return false;
default:
return true;
}
}
}
return true;
}
public static bool MapLessEquals<K, V>(this MapSet<K, V> left, MapSet<K, V> right)
{
var result = false;
if (!left.Keys.Except(right.Keys).Any() && left.Keys.Count() <= right.Keys.Count())
{
return left.All(kv => kv.Value.All(n => right[kv.Key].Contains(n)));
//&& right.All(kv => kv.Value.IsSubsetOf(left[kv.Key]));
}
return result;
}
public static bool MapLessEquals<K, V>(this MapSet<K, V> left, MapSet<K, V> right)
{
var result = false;
if (!left.Keys.Except(right.Keys).Any() && left.Keys.Count() <= right.Keys.Count())
{
return left.All(kv => kv.Value.All(n => right[kv.Key].Contains(n)));
//&& right.All(kv => kv.Value.IsSubsetOf(left[kv.Key]));
}
return result;
}
public static string FullName(this ITypeReference tref)
{
return TypeHelper.GetTypeName(tref, NameFormattingOptions.Signature | NameFormattingOptions.TypeParameters);
}
public static string GetName(this ITypeReference tref)
{
if (tref is INamedTypeReference)
return (tref as INamedTypeReference).Name.Value;
public static string FullName(this ITypeReference tref)
{
return TypeHelper.GetTypeName(tref, NameFormattingOptions.Signature | NameFormattingOptions.TypeParameters);
}
public static string GetName(this ITypeReference tref)
{
if (tref is INamedTypeReference)
return (tref as INamedTypeReference).Name.Value;
return TypeHelper.GetTypeName(tref, NameFormattingOptions.OmitContainingType | NameFormattingOptions.OmitContainingNamespace | NameFormattingOptions.SmartTypeName);
}
public static string GetNameThatMatchesReflectionName(this ITypeDefinition typeDefinition)
{
return Microsoft.Cci.TypeHelper.GetTypeName(typeDefinition, NameFormattingOptions.OmitContainingType | NameFormattingOptions.OmitContainingNamespace | NameFormattingOptions.UseGenericTypeNameSuffix);
}
return TypeHelper.GetTypeName(tref, NameFormattingOptions.OmitContainingType | NameFormattingOptions.OmitContainingNamespace | NameFormattingOptions.SmartTypeName);
}
public static string GetNameThatMatchesReflectionName(this ITypeDefinition typeDefinition)
{
return Microsoft.Cci.TypeHelper.GetTypeName(typeDefinition, NameFormattingOptions.OmitContainingType | NameFormattingOptions.OmitContainingNamespace | NameFormattingOptions.UseGenericTypeNameSuffix);
}
}
#region Methods to Compute a sort of propagation of Equalities
public static void PropagateExpressions(this ControlFlowGraph cfg, IDictionary<IVariable, IExpression> equalities)
{
foreach (var node in cfg.ForwardOrder)
{
PropagateExpressions(node, equalities);
}
}
private static void PropagateExpressions(CFGNode node, IDictionary<IVariable, IExpression> equalities)
{
foreach (var instruction in node.Instructions)
{
PropagateExpressions(instruction, equalities);
}
}
private static void PropagateExpressions(Instruction instruction, IDictionary<IVariable, IExpression> equalities)
{
var definition = instruction as DefinitionInstruction;
if (definition != null && definition.HasResult)
{
var expr = definition.ToExpression().ReplaceVariables(equalities);
equalities.Add(definition.Result, expr);
}
}
#endregion
}
}