private static void FindInputs(Instruction instruction, InstructionInputList inputs, List <Instruction> seen, VariableLocation location) { if (instruction == null || seen.Contains(instruction)) { return; } seen.Add(instruction); var expression = instruction as ExpressionInstruction; if (expression != null) { foreach (var statement in expression.Statements) { statement.FindInputs(inputs, location); } } var variableFields = instruction.GetType().GetFields().Where(field => field.FieldType == typeof(VariableReference)); var promptFields = instruction.GetType().GetFields().Where(field => field.FieldType == typeof(PromptString)); var instructionFields = instruction.GetType().GetFields().Where(field => typeof(Instruction).IsAssignableFrom(field.FieldType)); var instructionListFields = instruction.GetType().GetFields().Where(field => field.FieldType.IsGenericType && field.FieldType.GetGenericTypeDefinition() == typeof(List <>) && typeof(Instruction).IsAssignableFrom(field.FieldType.GetGenericArguments()[0])); foreach (var field in variableFields) { var value = field.GetValue(instruction) as VariableReference; if (value != null && value.Location == location) { inputs.Add(value, field); } } foreach (var field in promptFields) { var value = field.GetValue(instruction) as PromptString; if (value != null) { foreach (var input in value.Input) { if (input != null && input.Location == location) { inputs.Add(input, field); } } } } foreach (var field in instructionFields) { var value = field.GetValue(instruction) as Instruction; FindInputs(value, inputs, seen, location); } foreach (var listField in instructionListFields) { var instructions = listField.GetValue(instruction) as IList <Instruction>; for (var i = 0; i < instructions.Count; i++) { var value = instructions[i] as Instruction; FindInputs(value, inputs, seen, location); } } }