private static bool TryReplaceUsesInFlow( BlockFlow flow, IReadOnlyDictionary <ValueTag, ValueTag> replacementMap, out BlockFlow newFlow) { bool replacedAny = false; var instructions = flow.Instructions; var newInstructions = new Instruction[instructions.Count]; for (int i = 0; i < newInstructions.Length; i++) { Instruction newInsn; if (TryReplaceUsesInInstruction(instructions[i], replacementMap, out newInsn)) { newInstructions[i] = newInsn; replacedAny = true; } else { newInstructions[i] = instructions[i]; } } var branches = flow.Branches; var newBranches = new Branch[branches.Count]; for (int i = 0; i < newBranches.Length; i++) { var branch = branches[i]; var newArgs = new BranchArgument[branch.Arguments.Count]; for (int j = 0; j < newArgs.Length; j++) { var arg = branch.Arguments[j]; ValueTag value; if (arg.IsValue && replacementMap.TryGetValue(arg.ValueOrNull, out value) && value != arg.ValueOrNull) { newArgs[j] = BranchArgument.FromValue(value); replacedAny = true; } else { newArgs[j] = arg; } } newBranches[i] = branch.WithArguments(newArgs); } if (replacedAny) { newFlow = flow.WithBranches(newBranches).WithInstructions(newInstructions); } else { newFlow = flow; } return(replacedAny); }
/// <summary> /// Creates a new branch by applying a mapping to every value in /// this branch's argument list. /// </summary> /// <param name="mapping"> /// The mapping to apply to every value in this branch's /// argument list. /// </param> /// <returns>A new branch.</returns> public Branch MapArguments(Func <ValueTag, ValueTag> mapping) { return(MapArguments( arg => arg.IsValue ? BranchArgument.FromValue(mapping(arg.ValueOrNull)) : arg)); }
/// <summary> /// Creates a branch that is the result of appending /// an argument at the end of this branch's argument list. /// </summary> /// <param name="argument">The argument to add.</param> /// <returns>A new branch.</returns> public Branch AddArgument(ValueTag argument) { return(AddArgument(BranchArgument.FromValue(argument))); }