| File: Linker.Dataflow\ScannerExtensions.cs | Web Access |
| Project: src\runtime\src\tools\illink\src\linker\Mono.Linker.csproj (illink) |
// Copyright (c) .NET Foundation and contributors. All rights reserved. // Licensed under the MIT license. See LICENSE file in the project root for full license information. using System; using System.Collections.Generic; using Mono.Cecil.Cil; namespace Mono.Linker.Dataflow { static class ScannerExtensions { public static bool IsControlFlowInstruction(in this OpCode opcode) { return opcode.FlowControl == FlowControl.Branch || opcode.FlowControl == FlowControl.Cond_Branch || (opcode.FlowControl == FlowControl.Return && opcode.Code != Code.Ret); } public static HashSet<int> ComputeBranchTargets(this MethodIL methodIL) { HashSet<int> branchTargets = new HashSet<int>(); foreach (Instruction operation in methodIL.Instructions) { if (!operation.OpCode.IsControlFlowInstruction()) continue; object value = operation.Operand; if (value is Instruction inst) { branchTargets.Add(inst.Offset); } else if (value is Instruction[] instructions) { foreach (Instruction switchLabel in instructions) { branchTargets.Add(switchLabel.Offset); } } } foreach (ExceptionHandler einfo in methodIL.ExceptionHandlers) { if (einfo.HandlerType == ExceptionHandlerType.Filter) { branchTargets.Add(einfo.FilterStart.Offset); } branchTargets.Add(einfo.HandlerStart.Offset); } return branchTargets; } } }