public static void Evaluate(ParsedExpressionList expressionList, SDFState state) { Object lastExpressionObject = null; foreach (Object o in expressionList) { if (o is ParsedExpressionList) { if (lastExpressionObject != null) { state += lastExpressionObject; try { Evaluate((ParsedExpressionList) o, state); } finally { state -= lastExpressionObject; } lastExpressionObject = null; } } else { ParsedExpression expression = (ParsedExpression) o; MethodInfo method = expression.Expression.GetType().GetMethod("Evaluate"); lastExpressionObject = method.Invoke(expression.Expression, new Object[] { state, expression.ExpressionName, expression.Arguments }); } } }
public static ParsedExpressionList Parse(string expressions) { Regex regex = new Regex(@"\n?(?<indent>[ \t]*)(?<expression>\S+)(\s+(?<name>[^ \t=]+)\s*=\s*'(?<value>[^']+)')*"); ParsedExpressionList currentList = new ParsedExpressionList(); ParsedExpressionList rootList = currentList; int lastIndentLevel = -1; Stack expressionListStack = new Stack(); foreach (Match match in regex.Matches(expressions)) { string expression = null; Hashtable arguments = null; int currentIndentLevel = match.Groups["indent"].Length; { Group names = match.Groups["name"]; Group values = match.Groups["value"]; expression = match.Groups["expression"].ToString(); arguments = new Hashtable(names.Captures.Count); for (int counter = 0;counter < names.Captures.Count;++counter) { arguments[names.Captures[counter].ToString()] = values.Captures[counter].ToString(); } } if (lastIndentLevel == -1) { lastIndentLevel = currentIndentLevel; } if (currentIndentLevel > lastIndentLevel) { ParsedExpressionList lastList = currentList; // Push the current guy on the stack, set up a new one expressionListStack.Push(currentList); currentList = new ParsedExpressionList(); lastList += currentList; } else if (currentIndentLevel < lastIndentLevel) { // Pop lists until we get to this level while (currentIndentLevel < currentList.IndentLevel) { currentList = (ParsedExpressionList) expressionListStack.Pop(); } } currentList += new ParsedExpression(expression, arguments, currentIndentLevel); lastIndentLevel = currentIndentLevel; } return rootList; }
public void AddExpressionList(ParsedExpressionList parsedExpressionList) { this.expressionList.Add(parsedExpressionList); }
public void PostCreateExpression(SDFState state, string name, Hashtable arguments, ParsedExpressionList children) { this.rootExpressionChildren = children; }
public void PostCreateExpression(SDFState state, string name, Hashtable arguments, ParsedExpressionList children) { ((ExpressionRegistry) state[typeof(ExpressionRegistry)]).AddAssembly(arguments["filename"].ToString()); }
public static void Load(ParsedExpressionList expressionList, SDFState state, ProvidedStatePile parentExpressionStatePile) { ExpressionRegistry expressions = (ExpressionRegistry) state[typeof(ExpressionRegistry)]; ParsedExpression expression = null; TokenStringRegistry tokenStringRegistry = (TokenStringRegistry) state[typeof(TokenStringRegistry)]; foreach (Object o in expressionList) { if (o is ParsedExpressionList) { MaybeCallPostCreateExpression(state, expression, (ParsedExpressionList) o); parentExpressionStatePile.AddProvidedStateFromObject(expression.Expression); expression = null; Load((ParsedExpressionList) o, state, parentExpressionStatePile); parentExpressionStatePile.RemoveLastProvidedState(); } else { if (expression != null) { MaybeCallPostCreateExpression(state, expression, null); } expression = (ParsedExpression) o; BindArguments(expression.Arguments, tokenStringRegistry); { object newObject = null; object foundObject = expressions[expression.ExpressionName]; Type type = foundObject as Type; if ((foundObject != null) && (type == null)) { type = foundObject.GetType(); } if (type == null) { throw new SDFException(String.Format("Unknown expression '{0}'", expression.ExpressionName)); } { MethodInfo method = type.GetMethod("CreateExpression"); if (method != null) { newObject = method.Invoke(foundObject, new Object[] { state, expression.ExpressionName, expression.Arguments }); type = newObject.GetType(); } else { newObject = type.GetConstructor(new Type[0]).Invoke(null); } } { // On the class, see if there are SDFArgument attributes foreach (SDFArgumentAttribute argument in type.GetCustomAttributes(typeof(SDFArgumentAttribute), false)) { // If the argument is required, then whine if it wasn't specified if ((argument.Required) && (!expression.Arguments.Contains(argument.Name))) { throw new SDFException(String.Format("Rquired argument '{0}' was not specified", argument.Name)); } } } // Set arguments to properties if required { // For each property, check to see if it has an SDFArgument attribute foreach (PropertyInfo property in type.GetProperties()) { foreach (SDFArgumentAttribute argument in property.GetCustomAttributes(typeof(SDFArgumentAttribute), false)) { // If the argument is required, then whine if it wasn't specified if ((argument.Required) && (!expression.Arguments.Contains(property.Name))) { throw new SDFException(String.Format("Rquired argument '{0}' was not specified", property.Name)); } // Set the property property.GetSetMethod().Invoke(newObject, new Object[] { expression.Arguments[property.Name] }); } } } { MethodInfo method = type.GetMethod("Evaluate"); // Now check to see if there's any required state foreach (SDFStateRequiredAttribute stateRequired in method.GetCustomAttributes(typeof(SDFStateRequiredAttribute), false)) { if ((state[stateRequired.RequiredType] == null) && (!parentExpressionStatePile.Contains(stateRequired.RequiredType))) { throw new SDFException(String.Format("Required state '{0}' was not found", stateRequired.RequiredType.Name)); } } } expression.Expression = newObject; } } } if (expression != null) { MaybeCallPostCreateExpression(state, expression, null); expression = null; } }
private static void MaybeCallPostCreateExpression(SDFState state, ParsedExpression expression, ParsedExpressionList children) { MethodInfo postCreateMethod = expression.Expression.GetType().GetMethod("PostCreateExpression"); if (postCreateMethod != null) { postCreateMethod.Invoke(expression.Expression, new Object[] { state, expression.ExpressionName, expression.Arguments, children }); } }