/// <summary> /// Restores the former state of a pipeline from Xml. /// </summary> /// <param name="pipeline">The <see cref="XDocument"/> describing the /// pipeline.</param> /// <returns>The set of processes within the pipeline as described in /// the Xml.</returns> public Client.PipelineDefinition RestorePipeline(XDocument pipeline) { if (pipeline == null) { return(new Client.PipelineDefinition()); } var factories = _repo.ToDictionary(); PipelineXmlDecompiler decompiler = new PipelineXmlDecompiler(factories); DecompilationVisitor visitor = new DecompilationVisitor(decompiler); PipelineXmlValidator validator = new PipelineXmlValidator(visitor, factories.Keys); validator.ThrowOnError = true; XmlTraverser traverser = new XmlTraverser(validator); try { traverser.Traverse(pipeline); var algorithms = visitor.Algorithms; _updateAlgorithmNames(algorithms); return(new Client.PipelineDefinition(algorithms)); } catch (Exception e) { throw new ArgumentException("Error restoring Pipeline Xml.", e); } }
public void CFGCreator_RootAndExitIsStmtClassMethod(string phpcode) { var extract = ParseAndExtract(phpcode); foreach (var @class in extract.Classes) { foreach (var method in @class.Methods) { var ast = method.AstNode; var traverser = new XmlTraverser(); var cfgcreator = new CFGCreator(); traverser.AddVisitor(cfgcreator); traverser.Traverse(ast); var graph = cfgcreator.Graph; //Root assertions Assert.AreEqual(AstConstants.Nodes.Stmt_ClassMethod, graph.Vertices.First().ToString()); graph.AssertInEdges(graph.Vertices.First(), 0, "Entry node - in edges"); graph.AssertOutEdges(graph.Vertices.First(), 1, "Entry node - out edges"); Assert.AreEqual(true, graph.Vertices.First().IsRoot); //Leaf assertions graph.AssertOutEdges(graph.Vertices.ElementAt(1), 0, "Exit node - out edges"); Assert.AreEqual(true, graph.Vertices.ElementAt(1).IsLeaf); } } }
public void CFGCreator_RootAndExitIsClousure(string phpCode) { var extract = ParseAndExtract(phpCode); foreach (var closure in extract.Closures) { var ast = closure.AstNode; var traverser = new XmlTraverser(); var cfgcreator = new CFGCreator(); traverser.AddVisitor(cfgcreator); traverser.Traverse(ast); var graph = cfgcreator.Graph; //Root Assert.IsTrue(graph.Vertices.First().IsRoot, "the first vertix is not the root node"); Assert.IsTrue(graph.Vertices.First().IsSpecialBlock, "The first node was not marked with IsSpecialBlock"); graph.AssertInEdges(graph.Vertices.First(), 0, "Entry node contains in edges"); graph.AssertOutEdges(graph.Vertices.First(), 1, "Entry node did not have exactly one out edge"); Assert.AreEqual(AstConstants.Nodes.Expr_Closure, graph.Vertices.First().ToString(), "The root node was not a closure, and was expected to be a closure"); //Leaf Assert.IsTrue(graph.Vertices.ElementAt(1).IsLeaf, "The element at position one was not the exit block"); Assert.IsTrue(graph.Vertices.ElementAt(1).IsSpecialBlock, "The element at position one was not marked with IsSpecialBlock"); graph.AssertOutEdges(graph.Vertices.ElementAt(1), 0, "The exit block contained out edged"); Assert.AreEqual(AstConstants.Nodes.Expr_Closure, graph.Vertices.ElementAt(1).ToString()); } }
public void CFGCreator_RootAndExitIsStmtFunction(string phpcode) { var extract = ParseAndExtract(phpcode); foreach (var func in extract.Functions) { var ast = func.AstNode; var traverser = new XmlTraverser(); var cfgcreator = new CFGCreator(); traverser.AddVisitor(cfgcreator); traverser.Traverse(ast); var graph = cfgcreator.Graph; //Root assertions Assert.IsTrue(graph.Vertices.First().IsRoot, "first node was not the root node"); Assert.IsTrue(graph.Vertices.First().IsSpecialBlock, "first node was not marked as IsSpecialBlock"); graph.AssertInEdges(graph.Vertices.First(), 0, "Entry node - in edges"); graph.AssertOutEdges(graph.Vertices.First(), 1, "Entry node - out edges"); Assert.AreEqual(AstConstants.Nodes.Stmt_Function, graph.Vertices.First().ToString()); //Leaf assertions Assert.IsTrue(graph.Vertices.ElementAt(1).IsSpecialBlock, "The element at position 1 was not marked with IsSpecialBlock"); Assert.AreEqual(true, graph.Vertices.ElementAt(1).IsLeaf, "The element at position 1 was not marked with IsLeaf"); graph.AssertOutEdges(graph.Vertices.ElementAt(1), 0, "Exit node - out edges"); } }
private static File BuildFileCFGAndExtractFileInformation(KeyValuePair <string, XmlDocument> parsedFile) { var traverser = new XmlTraverser(); var metricAnalyzer = new MetricVisitor(); var extractor = new ClassAndFunctionExtractor(); var printer = new ASTPrinter(Console.Out); var cfgcreator = new CFGCreator(); traverser.AddVisitor(extractor); traverser.AddVisitor(metricAnalyzer); traverser.AddVisitor(cfgcreator); //traverser.AddVisitor(printer); traverser.AddVisitors(_components.AstVisitors.ToArray()); traverser.Traverse(parsedFile.Value.FirstChild.NextSibling); foreach (var function in extractor.Functions) { function.File = parsedFile.Key; } foreach (var closure in extractor.Closures) { closure.File = parsedFile.Key; } _funcHandler.CustomFunctions.AddRange(extractor.Functions); foreach (var @class in extractor.Classes) { @class.File = parsedFile.Key; foreach (var method in @class.Methods) { //HACK: This is not a good way to handle this! Should we add a new derived function class called method that includes the class name //-||-: and make a special list for them in the function handler, or is this okay? method.Name = @class.Name + "->" + method.Name; method.File = parsedFile.Key; _funcHandler.CustomFunctions.Add(method); } } //cfgcreator.Graph.VisualizeGraph("graph", Program.Configuration.GraphSettings); var cfgPruner = new CFGPruner(); cfgPruner.Prune(cfgcreator.Graph); //cfgcreator.Graph.VisualizeGraph("graph-pruned", Configuration.GraphSettings); File file = new File(parsedFile.Value) { CFG = cfgcreator.Graph, FullPath = parsedFile.Key, Interfaces = extractor.Interfaces.GroupBy(i => i.Name, i => i).ToDictionary(i => i.Key, i => i.ToList()), Classes = extractor.Classes.GroupBy(c => c.Name, c => c).ToDictionary(c => c.Key, c => c.ToList()), Closures = extractor.Closures.ToArray(), Functions = extractor.Functions.GroupBy(i => i.Name, i => i).ToDictionary(i => i.Key, i => i.ToList()) }; return(file); }
public static T ParseAndIterate <T>(string phpCode, string phpParser) where T : IXmlVisitor, new() { XmlNode ast = ParsePHPCode(phpCode, phpParser); var traverser = new XmlTraverser(); var visitor = new T(); traverser.AddVisitor(visitor); traverser.Traverse(ast.FirstChild.NextSibling); return(visitor); }
/// <summary> /// Analyses a custom function in for security issues, with the currenctly known taint for actual parameters. /// </summary> /// <returns>A TainSets for the custom function that is being analyzed</returns> /// <param name="customFunction">Custom function object to perform the analysis on</param> /// <param name="varStorage">The currently known variable storage (this is to included because of superglobals, globals etc.)</param> /// <param name="paramActualVals">Parameter actual values</param> /// <param name="resolver">File inclusion resolver</param> /// <param name="includeStack">Currently known includes</param> /// <param name="functionCalls">Currently known function calls</param> internal ExpressionInfo AnalyseCustomFunction(Function customFunction, ImmutableVariableStorage varStorage, IVulnerabilityStorage vulnerabilityStorage, IList <ExpressionInfo> paramActualVals, IIncludeResolver resolver, AnalysisStacks stacks) { var stmts = customFunction.AstNode.GetSubNode(AstConstants.Subnode + ":" + AstConstants.Subnodes.Stmts).FirstChild; var traverser = new XmlTraverser(); var cfgcreator = new CFGCreator(); traverser.AddVisitor(cfgcreator); traverser.Traverse(stmts); var cfgPruner = new CFGPruner(); cfgPruner.Prune(cfgcreator.Graph); var initialTaint = varStorage.ToMutable(); initialTaint.SuperGlobals.Clear(); initialTaint.SuperGlobals.AddRange(varStorage.SuperGlobals); initialTaint.LocalVariables.Clear(); initialTaint.LocalAccessibleGlobals.Clear(); for (int i = 1; i <= paramActualVals.Count; i++) { var paramFormal = customFunction.Parameters.FirstOrDefault(x => x.Key.Item1 == i); if (paramFormal.Value == null) { continue; } var @var = new Variable(paramFormal.Value.Name, VariableScope.Function) { Info = paramActualVals[i - 1].ValueInfo }; initialTaint.LocalVariables.Add(paramFormal.Value.Name, @var); } var blockAnalyzer = new TaintBlockAnalyzer(vulnerabilityStorage, resolver, AnalysisScope.Function, fileAnalyzer, stacks, subroutineAnalyzerFactory, _funcHandler); blockAnalyzer.AnalysisExtensions.AddRange(AnalysisExtensions); var condAnalyser = new ConditionTaintAnalyser(AnalysisScope.Function, resolver, stacks.IncludeStack, _funcHandler); var cfgTaintAnalysis = new TaintAnalysis(blockAnalyzer, condAnalyser, ImmutableVariableStorage.CreateFromMutable(initialTaint)); //var taintAnalysis = new CFGTraverser(new ForwardTraversal(), cfgTaintAnalysis, new QueueWorklist()); var taintAnalysis = new CFGTraverser(new ForwardTraversal(), cfgTaintAnalysis, new ReversePostOrderWorkList(cfgcreator.Graph)); taintAnalysis.Analyze(cfgcreator.Graph); var exprInfoAll = new ExpressionInfo(); foreach (ExpressionInfo exprInfo in blockAnalyzer.ReturnInfos) { exprInfoAll = exprInfoAll.Merge(exprInfo); } return(exprInfoAll); }
private ReachingSet AnalyzeNode(TaggedEdge <CFGBlock, EdgeTag> edge) { if (ReachingSetDictionary[edge.Source] == null) { ReachingSetDictionary = ReachingSetDictionary.SetItem(edge.Source, new ReachingSet()); } if (ReachingSetDictionary[edge.Target] == null) { ReachingSetDictionary = ReachingSetDictionary.SetItem(edge.Target, new ReachingSet()); } var node = edge.Target; // IN: // U RD_OUT(l') // (l'~>l) ReachingSetDictionary = ReachingSetDictionary.SetItem(node, ReachingSetDictionary[node].AddInVarRange(ReachingSetDictionary[edge.Source].DefinedOutVars, true)); // OUT: // (RD_IN(l) \ kill(l)) U gen(l) var Out = ReachingSetDictionary[node]; Out = Out.AddOutVarRange(ReachingSetDictionary[node].DefinedInVars); XmlTraverser xmlTraverser = new XmlTraverser(); CFGASTNodeVisitor nodeVisitor = new CFGASTNodeVisitor(); xmlTraverser.AddVisitor(nodeVisitor); if (node.AstEntryNode != null) { var nodeToTraverse = Conditional.HasConditionNode(node.AstEntryNode) ? Conditional.GetCondNode(node.AstEntryNode) : node.AstEntryNode; xmlTraverser.Traverse(nodeToTraverse); foreach (var currNode in nodeVisitor.NodesOfInterest) { var varNode = AstNodeInfo.GetVarNameXmlNode(currNode); ValueInfo varInfo = new ValueInfo() { Block = node }; varInfo = VariableInfoComposer.AnalyzeBlock(varInfo); var gs = new Variable(AstNodeInfo.GetVarNameXmlNode(currNode).Name, VariableScope.Unknown); gs = gs.AddVarInfo(varInfo); Out = Out.AddOutVar(varNode.InnerText, gs); } } ReachingSetDictionary = ReachingSetDictionary.SetItem(node, ReachingSetDictionary[node].AddOutVarRange(Out.DefinedOutVars)); return(ReachingSetDictionary[node]); }
private static void WPGotoAnalysis(Arguments arguments, Config configuration) { var v = Stopwatch.StartNew(); var folders = Directory.GetDirectories(@"G:\WP"); int counter = 0; var progress = new BikeGuyRidingAnimation(folders.Count()); var locker = new object(); Parallel.ForEach(folders, new ParallelOptions() { MaxDegreeOfParallelism = 7 }, folder => { int myNumber = Interlocked.Increment(ref counter); arguments.Target = Path.Combine(arguments.Target, folder); if (!Directory.Exists(arguments.Target)) { return; } var projectParser = new ProjectParser(arguments.Target, configuration.PHPSettings); ParseResult parseResult = projectParser.ParseProjectFiles(); foreach (var parsedFile in parseResult.ParsedFiles) { //Console.WriteLine("File: " + parsedFile.Key); var traverser = new XmlTraverser(); var metricVisitor = new MetricVisitor(); traverser.AddVisitor(metricVisitor); traverser.Traverse(parsedFile.Value); if (metricVisitor.Gotos > 0) { lock (locker) { System.IO.File.AppendAllLines(@"C:/pluginDLMessages.txt", new [] { "Goto found in " + parsedFile.Key }); } } } //Console.WriteLine(folder); if ((myNumber % 250) == 0) { Console.WriteLine(myNumber + " plugins scanned.."); } }); Console.WriteLine(v.Elapsed); Environment.Exit(1); }