ControlFlowBuilder 類別

定義

在方法主體中發出分支和例外狀況區塊。

public ref class ControlFlowBuilder sealed
public sealed class ControlFlowBuilder
type ControlFlowBuilder = class
Public NotInheritable Class ControlFlowBuilder
繼承
ControlFlowBuilder

範例

此範例示範如何使用 發出具有例外狀況處理程式 ControlFlowBuilder的方法主體:

// The following code emits method body similar to this C# code:

/* public static void ExceptionBlockTest(int x, int y)
   {
      try
      {
         Console.WriteLine(x / y);
      }
      catch (DivideByZeroException)
      {
         Console.WriteLine("Error: division by zero");
      }
   }
*/

public static InstructionEncoder ControlFlowBuilderDemo(MetadataBuilder metadata, 
    AssemblyReferenceHandle corlibAssemblyRef)
{
    var codeBuilder = new BlobBuilder();
    var flowBuilder = new ControlFlowBuilder();
    var encoder = new InstructionEncoder(codeBuilder, flowBuilder);

    // Get reference to System.Console
    AssemblyReferenceHandle systemConsoleAssemblyRef = metadata.AddAssemblyReference(
        name: metadata.GetOrAddString("System.Console"),
        version: new Version(4, 0, 0, 0),
        culture: default(StringHandle),
        publicKeyOrToken: default(BlobHandle),
        flags: default(AssemblyFlags),
        hashValue: default(BlobHandle));
    
    TypeReferenceHandle consoleTypeRefHandle = metadata.AddTypeReference(
        systemConsoleAssemblyRef,
        metadata.GetOrAddString("System"),
        metadata.GetOrAddString("Console"));

    // Get reference to void System.Console::WriteLine(int32)
    var methodSignature = new BlobBuilder();

    new BlobEncoder(methodSignature).
        MethodSignature(isInstanceMethod: false).
        Parameters(1, returnType => returnType.Void(), parameters => parameters.AddParameter().Type().Int32());

    BlobHandle sigBlobIndex1 = metadata.GetOrAddBlob(methodSignature);

    MemberReferenceHandle refWriteLineInt32 = metadata.AddMemberReference(
        consoleTypeRefHandle,
        metadata.GetOrAddString("WriteLine"),
        sigBlobIndex1);

    // Get reference to void System.Console::WriteLine(string)
    methodSignature = new BlobBuilder();

    new BlobEncoder(methodSignature).
        MethodSignature(isInstanceMethod: false).
        Parameters(1, returnType => returnType.Void(), parameters => parameters.AddParameter().Type().String());

    BlobHandle sigBlobIndex2 = metadata.GetOrAddBlob(methodSignature);

    MemberReferenceHandle refWriteLineString = metadata.AddMemberReference(
        consoleTypeRefHandle,
        metadata.GetOrAddString("WriteLine"),
        sigBlobIndex2);

    // Get reference to System.DivideByZeroException
    TypeReferenceHandle exceptionTypeRefHandle = metadata.AddTypeReference(
        corlibAssemblyRef,
        metadata.GetOrAddString("System"),
        metadata.GetOrAddString("DivideByZeroException"));
    
    LabelHandle labelTryStart = encoder.DefineLabel();
    LabelHandle labelTryEnd = encoder.DefineLabel();
    LabelHandle labelCatchStart = encoder.DefineLabel();
    LabelHandle labelCatchEnd = encoder.DefineLabel();
    LabelHandle labelExit = encoder.DefineLabel();

    flowBuilder.AddCatchRegion(labelTryStart, labelTryEnd, labelCatchStart, labelCatchEnd,
        exceptionTypeRefHandle);

    // .try {
    encoder.MarkLabel(labelTryStart);

    // ldarg.0
    encoder.OpCode(ILOpCode.Ldarg_0);

    // ldarg.1
    encoder.OpCode(ILOpCode.Ldarg_1);

    // div
    encoder.OpCode(ILOpCode.Div);

    // call void [System.Console]System.Console::WriteLine(int32)
    encoder.Call(refWriteLineInt32);

    // leave.s EXIT            
    encoder.Branch(ILOpCode.Leave_s, labelExit);
    encoder.MarkLabel(labelTryEnd);

    // } 
    // catch [System.Runtime]System.DivideByZeroException {
    encoder.MarkLabel(labelCatchStart);

    // pop
    encoder.OpCode(ILOpCode.Pop);
    
    // ldstr "Error: division by zero"
    encoder.LoadString(metadata.GetOrAddUserString("Error: division by zero"));

    // call void [System.Console]System.Console::WriteLine(string)
    encoder.Call(refWriteLineString);

    // leave.s EXIT            
    encoder.Branch(ILOpCode.Leave_s, labelExit);
    encoder.MarkLabel(labelCatchEnd);

    // } EXIT: ret
    encoder.MarkLabel(labelExit);
    encoder.OpCode(ILOpCode.Ret);
    
    return encoder;
}

備註

類別 ControlFlowBuilder 是用來在編碼 InstructionEncoder的方法主體中建立分支和例外狀況區塊。 如需發出 .NET 元件的詳細資訊,請參閱 MetadataBuilder 類別檔。

建構函式

ControlFlowBuilder()

在方法主體中發出分支和例外狀況區塊。

方法

AddCatchRegion(LabelHandle, LabelHandle, LabelHandle, LabelHandle, EntityHandle)

新增 catch 區域。

AddFaultRegion(LabelHandle, LabelHandle, LabelHandle, LabelHandle)

新增 fault 區域。

AddFilterRegion(LabelHandle, LabelHandle, LabelHandle, LabelHandle, LabelHandle)

新增 catch 區域。

AddFinallyRegion(LabelHandle, LabelHandle, LabelHandle, LabelHandle)

新增最後的區域。

Clear()

清除物件的內部狀態,允許重複使用相同的實例。

Equals(Object)

判斷指定的物件是否等於目前的物件。

(繼承來源 Object)
GetHashCode()

做為預設雜湊函式。

(繼承來源 Object)
GetType()

取得目前執行個體的 Type

(繼承來源 Object)
MemberwiseClone()

建立目前 Object 的淺層複製。

(繼承來源 Object)
ToString()

傳回代表目前物件的字串。

(繼承來源 Object)

適用於