private void CheckLHSAssign(ExpressionAst lhs, BitArray assignedBitArray) { ConvertExpressionAst ast = lhs as ConvertExpressionAst; Type convertType = null; if (ast != null) { lhs = ast.Child; convertType = ast.StaticType; } VariableExpressionAst item = lhs as VariableExpressionAst; VariablePath variablePath = item.VariablePath; if (variablePath.IsAnyLocal()) { string unaliasedVariableName = GetUnaliasedVariableName(variablePath); if ((convertType == null) && (unaliasedVariableName.Equals("foreach", StringComparison.OrdinalIgnoreCase) || unaliasedVariableName.Equals("switch", StringComparison.OrdinalIgnoreCase))) { convertType = typeof(object); } VariableAnalysisDetails details = this.CheckLHSAssignVar(unaliasedVariableName, assignedBitArray, convertType); details.AssociatedAsts.Add(item); item.TupleIndex = details.LocalTupleIndex; item.Automatic = details.Automatic; } else { item.TupleIndex = -2; } }
private Tuple <Type, Dictionary <string, int> > FinishAnalysis(bool scriptCmdlet = false) { List <Block> list = Block.GenerateReverseDepthFirstOrder(this._entryBlock); BitArray assignedBitArray = new BitArray(this._variables.Count); list[0]._visitData = assignedBitArray; this.AnalyzeBlock(assignedBitArray, list[0]); for (int i = 1; i < list.Count; i++) { Block block = list[i]; assignedBitArray = new BitArray(this._variables.Count); assignedBitArray.SetAll(true); block._visitData = assignedBitArray; int num2 = 0; foreach (Block block2 in block._predecessors) { if (block2._visitData != null) { num2++; assignedBitArray.And((BitArray)block2._visitData); } } this.AnalyzeBlock(assignedBitArray, block); } var v = this._variables.Values.Where(x => x.LocalTupleIndex == -2).SelectMany(x => x.AssociatedAsts); foreach (Ast ast in v) { FixTupleIndex(ast, -2); } VariableAnalysisDetails[] detailsArray = (from details in this._variables.Values where details.LocalTupleIndex >= 0 orderby details.LocalTupleIndex select details).ToArray <VariableAnalysisDetails>(); Dictionary <string, int> dictionary = new Dictionary <string, int>(0, StringComparer.OrdinalIgnoreCase); for (int j = 0; j < detailsArray.Length; j++) { VariableAnalysisDetails details = detailsArray[j]; string name = details.Name; dictionary.Add(name, j); if (details.LocalTupleIndex != j) { foreach (Ast ast2 in details.AssociatedAsts) { FixTupleIndex(ast2, j); } } } return(Tuple.Create <Type, Dictionary <string, int> >(MutableTuple.MakeTupleType((from l in detailsArray select l.Type).ToArray <Type>()), dictionary)); }
private void AnalyzeBlock(BitArray assignedBitArray, Block block) { foreach (Ast ast in block._asts) { VariableExpressionAst ast2 = ast as VariableExpressionAst; if (ast2 != null) { VariablePath variablePath = ast2.VariablePath; if (variablePath.IsAnyLocal()) { string unaliasedVariableName = GetUnaliasedVariableName(variablePath); VariableAnalysisDetails details = this._variables[unaliasedVariableName]; if (details.Automatic) { ast2.TupleIndex = details.LocalTupleIndex; ast2.Automatic = true; } else { ast2.TupleIndex = (assignedBitArray[details.BitIndex] && !details.PreferenceVariable) ? details.LocalTupleIndex : -2; } } } else { AssignmentTarget target = ast as AssignmentTarget; if (target != null) { if (target._targetAst != null) { this.CheckLHSAssign(target._targetAst, assignedBitArray); } else { this.CheckLHSAssignVar(target._variableName, assignedBitArray, target._type); } } else { DataStatementAst item = ast as DataStatementAst; if (item != null) { VariableAnalysisDetails details2 = this.CheckLHSAssignVar(item.Variable, assignedBitArray, typeof(object)); item.TupleIndex = details2.LocalTupleIndex; details2.AssociatedAsts.Add(item); } } } } }
private void NoteVariable(string variableName, int index, Type type, bool automatic = false, bool preferenceVariable = false) { if (!this._variables.ContainsKey(variableName)) { VariableAnalysisDetails details = new VariableAnalysisDetails { BitIndex = this._variables.Count, LocalTupleIndex = index, Name = variableName, Type = type, Automatic = automatic, PreferenceVariable = preferenceVariable }; this._variables.Add(variableName, details); } }
private void NoteVariable(string variableName, int index, Type type, bool automatic = false, bool preferenceVariable = false) { if (!this._variables.ContainsKey(variableName)) { VariableAnalysisDetails details = new VariableAnalysisDetails { BitIndex = this._variables.Count, LocalTupleIndex = index, Name = variableName, Type = type, Automatic = automatic, PreferenceVariable = preferenceVariable }; this._variables.Add(variableName, details); } }
private Tuple <Type, Dictionary <string, int> > AnalyzeImpl(IParameterMetadataProvider ast, bool disableOptimizations, bool scriptCmdlet) { this._variables = FindAllVariablesVisitor.Visit(ast, disableOptimizations, scriptCmdlet, out this._localsAllocated, out this._disableOptimizations); this.Init(); if (ast.Parameters != null) { foreach (ParameterAst ast2 in ast.Parameters) { VariablePath variablePath = ast2.Name.VariablePath; if (variablePath.IsAnyLocal()) { bool flag = false; int num = -1; Type c = null; foreach (AttributeBaseAst ast3 in ast2.Attributes) { if (ast3 is TypeConstraintAst) { num++; if (c == null) { c = ast3.TypeName.GetReflectionType(); } } else { Type reflectionAttributeType = ast3.TypeName.GetReflectionAttributeType(); if (typeof(ValidateArgumentsAttribute).IsAssignableFrom(reflectionAttributeType) || typeof(ArgumentTransformationAttribute).IsAssignableFrom(reflectionAttributeType)) { flag = true; } } } string unaliasedVariableName = GetUnaliasedVariableName(variablePath); VariableAnalysisDetails details = this._variables[unaliasedVariableName]; c = c ?? (details.Type ?? typeof(object)); if (((flag || (num > 0)) || (typeof(PSReference).IsAssignableFrom(c) || MustBeBoxed(c))) && (!details.Automatic && !details.PreferenceVariable)) { details.LocalTupleIndex = -2; } this._entryBlock.AddAst(new AssignmentTarget(unaliasedVariableName, c)); } } } ast.Body.Accept(this); return(this.FinishAnalysis(scriptCmdlet)); }
public object VisitSwitchStatement(SwitchStatementAst switchStatementAst) { VariableAnalysisDetails details = this._variables["switch"]; if ((details.LocalTupleIndex == -1) && !this._disableOptimizations) { details.LocalTupleIndex = this._localsAllocated++; } Action generateCondition = delegate { switchStatementAst.Condition.Accept(this); this._currentBlock.AddAst(new AssignmentTarget("switch", typeof(IEnumerator))); }; Action generateLoopBody = delegate { bool flag = switchStatementAst.Default != null; Block next = new Block(); int count = switchStatementAst.Clauses.Count; for (int j = 0; j < count; j++) { Tuple <ExpressionAst, StatementBlockAst> tuple = switchStatementAst.Clauses[j]; Block block2 = new Block(); bool flag2 = (j == (count - 1)) && !flag; Block block3 = flag2 ? next : new Block(); tuple.Item1.Accept(this); this._currentBlock.FlowsTo(block3); this._currentBlock.FlowsTo(block2); this._currentBlock = block2; tuple.Item2.Accept(this); if (!flag2) { this._currentBlock.FlowsTo(block3); this._currentBlock = block3; } } if (flag) { this._currentBlock.FlowsTo(next); switchStatementAst.Default.Accept(this); } this._currentBlock.FlowsTo(next); this._currentBlock = next; }; this.GenerateWhileLoop(switchStatementAst.Label, generateCondition, generateLoopBody, null); return(null); }
public object VisitAssignmentStatement(AssignmentStatementAst assignmentStatementAst) { assignmentStatementAst.Right.Accept(this); foreach (ExpressionAst ast in GetAssignmentTargets(assignmentStatementAst.Left)) { bool flag = false; int num = 0; ExpressionAst child = ast; while (child is AttributedExpressionAst) { num++; if (!(child is ConvertExpressionAst)) { flag = true; } child = ((AttributedExpressionAst)child).Child; } if (child is VariableExpressionAst) { if (flag || (num > 1)) { VariablePath variablePath = ((VariableExpressionAst)child).VariablePath; if (variablePath.IsAnyLocal()) { VariableAnalysisDetails details = this._variables[GetUnaliasedVariableName(variablePath)]; details.LocalTupleIndex = -2; } } else { this._currentBlock.AddAst(new AssignmentTarget(ast)); } } else { ast.Accept(this); } } return(null); }
private VariableAnalysisDetails CheckLHSAssignVar(string variableName, BitArray assignedBitArray, Type convertType) { VariableAnalysisDetails details = this._variables[variableName]; if (details.LocalTupleIndex == -1) { details.LocalTupleIndex = (this._disableOptimizations || _allScopeVariables.ContainsKey(variableName)) ? -2 : this._localsAllocated++; } if ((convertType != null) && MustBeBoxed(convertType)) { details.LocalTupleIndex = -2; } Type o = details.Type; if (o == null) { details.Type = convertType ?? typeof(object); } else { if (!assignedBitArray[details.BitIndex] && (convertType == null)) { convertType = typeof(object); } if ((convertType != null) && !convertType.Equals(o)) { if (details.Automatic || details.PreferenceVariable) { details.Type = typeof(object); } else { details.LocalTupleIndex = -2; } } } assignedBitArray.Set(details.BitIndex, true); return(details); }
public object VisitForEachStatement(ForEachStatementAst forEachStatementAst) { VariableAnalysisDetails details = this._variables["foreach"]; if ((details.LocalTupleIndex == -1) && !this._disableOptimizations) { details.LocalTupleIndex = this._localsAllocated++; } Block afterFor = new Block(); Action generateCondition = delegate { forEachStatementAst.Condition.Accept(this); this._currentBlock.FlowsTo(afterFor); this._currentBlock.AddAst(new AssignmentTarget("foreach", typeof(IEnumerator))); this._currentBlock.AddAst(new AssignmentTarget(forEachStatementAst.Variable)); }; this.GenerateWhileLoop(forEachStatementAst.Label, generateCondition, delegate { forEachStatementAst.Body.Accept(this); }, null); this._currentBlock.FlowsTo(afterFor); this._currentBlock = afterFor; return(null); }
public object VisitVariableExpression(VariableExpressionAst variableExpressionAst) { VariablePath variablePath = variableExpressionAst.VariablePath; if (variablePath.IsAnyLocal()) { VariableAnalysisDetails details = this._variables[GetUnaliasedVariableName(variablePath)]; if (details.LocalTupleIndex != -1) { variableExpressionAst.TupleIndex = details.PreferenceVariable ? -2 : details.LocalTupleIndex; variableExpressionAst.Automatic = details.Automatic; } else { this._currentBlock.AddAst(variableExpressionAst); } details.AssociatedAsts.Add(variableExpressionAst); } else { variableExpressionAst.TupleIndex = -2; } return(null); }
private static void FixAssigned(Ast ast, VariableAnalysisDetails details) { var variableAst = ast as VariableExpressionAst; if (variableAst != null && details.Assigned) { variableAst.Assigned = true; } }