例外ブロックを終了します。
Public Overridable Sub EndExceptionBlock()
[C#]
public virtual void EndExceptionBlock();
[C++]
public: virtual void EndExceptionBlock();
[JScript]
public function EndExceptionBlock();
例外
例外の種類 | 条件 |
---|---|
InvalidOperationException | コード ストリームの予測されない場所で例外ブロックの終了が発生しました。 |
NotSupportedException | 生成されている MSIL (Microsoft intermediate language) は、現在例外ブロックに含まれていません。 |
使用例
[Visual Basic, C#, C++] EndExceptionBlock メソッドの実際の使用方法については、次のコード例を参照してください。
Imports System
Imports System.Threading
Imports System.Reflection
Imports System.Reflection.Emit
_
Class ILThrowExceptionDemo
Public Shared Function BuildAdderType() As Type
Dim myDomain As AppDomain = Thread.GetDomain()
Dim myAsmName As New AssemblyName()
myAsmName.Name = "AdderExceptionAsm"
Dim myAsmBldr As AssemblyBuilder = myDomain.DefineDynamicAssembly(myAsmName, _
AssemblyBuilderAccess.Run)
Dim myModBldr As ModuleBuilder = myAsmBldr.DefineDynamicModule("AdderExceptionMod")
Dim myTypeBldr As TypeBuilder = myModBldr.DefineType("Adder")
Dim adderParams() As Type = {GetType(Integer), GetType(Integer)}
' This method will add two numbers which are 100 or less. If either of the
' passed integer vales are greater than 100, it will throw an exception.
Dim adderBldr As MethodBuilder = myTypeBldr.DefineMethod("DoAdd", _
MethodAttributes.Public Or MethodAttributes.Static, _
GetType(Integer), adderParams)
Dim adderIL As ILGenerator = adderBldr.GetILGenerator()
' In order to successfully branch, we need to create labels
' representing the offset IL instruction block to branch to.
' These labels, when the MarkLabel(Label) method is invoked,
' will specify the IL instruction to branch to.
Dim exCtorInfo As ConstructorInfo = GetType(OverflowException).GetConstructor( _
New Type() {GetType(String)})
Dim exToStrMI As MethodInfo = GetType(OverflowException).GetMethod("ToString")
Dim writeLineMI As MethodInfo = GetType(Console).GetMethod("WriteLine", _
New Type() {GetType(String), _
GetType(Object)})
Dim tmp1 As LocalBuilder = adderIL.DeclareLocal(GetType(Integer))
Dim tmp2 As LocalBuilder = adderIL.DeclareLocal(GetType(OverflowException))
Dim failed As Label = adderIL.DefineLabel()
Dim endOfMthd As Label = adderIL.DefineLabel()
' First, load argument 0 and the integer value of "100" onto the
' stack. If arg0 > 100, branch to the label "failed", which is marked
' as the address of the block that throws an exception.
Dim exBlock As Label = adderIL.BeginExceptionBlock()
adderIL.Emit(OpCodes.Ldarg_0)
adderIL.Emit(OpCodes.Ldc_I4_S, 100)
adderIL.Emit(OpCodes.Bgt_S, failed)
' Now, check to see if argument 1 was greater than 100. If it was,
' branch to "failed." Otherwise, fall through and perform the addition,
' branching unconditionally to the instruction at the label "endOfMthd".
adderIL.Emit(OpCodes.Ldarg_1)
adderIL.Emit(OpCodes.Ldc_I4_S, 100)
adderIL.Emit(OpCodes.Bgt_S, failed)
adderIL.Emit(OpCodes.Ldarg_0)
adderIL.Emit(OpCodes.Ldarg_1)
adderIL.Emit(OpCodes.Add_Ovf_Un)
adderIL.Emit(OpCodes.Stloc_S, tmp1)
adderIL.Emit(OpCodes.Br_S, endOfMthd)
' If one of the arguments was greater than 100, we need to throw an
' exception. We'll use "OverflowException" with a customized message.
' First, we load our message onto the stack, and then create a new
' exception object using the constructor overload that accepts a
' string message.
adderIL.MarkLabel(failed)
adderIL.Emit(OpCodes.Ldstr, "Cannot accept values over 100 for add.")
adderIL.Emit(OpCodes.Newobj, exCtorInfo)
' We're going to need to refer to that exception object later, so let's
' store it in a temporary variable. Since the store function pops the
' the value/reference off the stack, and we'll need it to throw the
' exception, we will subsequently load it back onto the stack as well.
adderIL.Emit(OpCodes.Stloc_S, tmp2)
adderIL.Emit(OpCodes.Ldloc_S, tmp2)
' Throw the exception currently atop the stack.
adderIL.ThrowException(GetType(OverflowException))
' Start the catch block.
adderIL.BeginCatchBlock(GetType(OverflowException))
' First, we'll load a "wrapper" string, and then perform a
' late-bound call to the ToString() method of OverflowException,
' passing it the exception object we stored in local variable tmp2.
adderIL.Emit(OpCodes.Ldstr, "{0}")
adderIL.Emit(OpCodes.Ldloc_S, tmp2)
adderIL.EmitCall(OpCodes.Callvirt, exToStrMI, Nothing)
' Now, we should have the "wrapper" string atop the stack,
' along with the string result of the ToString() call. All
' conditions are met to call WriteLine(string, object).
adderIL.EmitCall(OpCodes.Call, writeLineMI, Nothing)
' Since our function has to return an integer value, we'll load -1 onto
' the stack to indicate an error, and store it in local variable tmp1.
adderIL.Emit(OpCodes.Ldc_I4_M1)
adderIL.Emit(OpCodes.Stloc_S, tmp1)
' End the exception handling block.
adderIL.EndExceptionBlock()
' The end of the method. If no exception was thrown, the correct value
' will be saved in tmp1. If an exception was thrown, tmp1 will be equal
' to -1. Either way, we'll load the value of tmp1 onto the stack and return.
adderIL.MarkLabel(endOfMthd)
adderIL.Emit(OpCodes.Ldloc_S, tmp1)
adderIL.Emit(OpCodes.Ret)
Return myTypeBldr.CreateType()
End Function 'BuildAdderType
Public Shared Sub Main()
Dim adderType As Type = BuildAdderType()
Dim addIns As Object = Activator.CreateInstance(adderType)
Dim addParams(1) As Object
Console.Write("Enter an integer value: ")
addParams(0) = CType(Convert.ToInt32(Console.ReadLine()), Object)
Console.Write("Enter another integer value: ")
addParams(1) = CType(Convert.ToInt32(Console.ReadLine()), Object)
Console.WriteLine("If either integer was > 100, an exception will be thrown.")
Console.WriteLine("---")
Console.WriteLine("{0} + {1} = {2}", addParams(0), addParams(1), _
adderType.InvokeMember("DoAdd", _
BindingFlags.InvokeMethod, _
Nothing, addIns, addParams))
End Sub 'Main
End Class 'ILThrowExceptionDemo
[C#]
using System;
using System.Threading;
using System.Reflection;
using System.Reflection.Emit;
class ILThrowExceptionDemo {
public static Type BuildAdderType() {
AppDomain myDomain = Thread.GetDomain();
AssemblyName myAsmName = new AssemblyName();
myAsmName.Name = "AdderExceptionAsm";
AssemblyBuilder myAsmBldr = myDomain.DefineDynamicAssembly(myAsmName,
AssemblyBuilderAccess.Run);
ModuleBuilder myModBldr = myAsmBldr.DefineDynamicModule("AdderExceptionMod");
TypeBuilder myTypeBldr = myModBldr.DefineType("Adder");
Type[] adderParams = new Type[] {typeof(int), typeof(int)};
// This method will add two numbers which are 100 or less. If either of the
// passed integer vales are greater than 100, it will throw an exception.
MethodBuilder adderBldr = myTypeBldr.DefineMethod("DoAdd",
MethodAttributes.Public |
MethodAttributes.Static,
typeof(int),
adderParams);
ILGenerator adderIL = adderBldr.GetILGenerator();
// representing the offset IL instruction block to branch to.
// These labels, when the MarkLabel(Label) method is invoked,
// will specify the IL instruction to branch to.
ConstructorInfo exCtorInfo = typeof(OverflowException).GetConstructor(
new Type[]
{typeof(string)});
MethodInfo exToStrMI = typeof(OverflowException).GetMethod("ToString");
MethodInfo writeLineMI = typeof(Console).GetMethod("WriteLine",
new Type[]
{typeof(string),
typeof(object)});
LocalBuilder tmp1 = adderIL.DeclareLocal(typeof(int));
LocalBuilder tmp2 = adderIL.DeclareLocal(typeof(OverflowException));
Label failed = adderIL.DefineLabel();
Label endOfMthd = adderIL.DefineLabel();
// First, load argument 0 and the integer value of "100" onto the
// stack. If arg0 > 100, branch to the label "failed", which is marked
// as the address of the block that throws an exception.
Label exBlock = adderIL.BeginExceptionBlock();
adderIL.Emit(OpCodes.Ldarg_0);
adderIL.Emit(OpCodes.Ldc_I4_S, 100);
adderIL.Emit(OpCodes.Bgt_S, failed);
// Now, check to see if argument 1 was greater than 100. If it was,
// branch to "failed." Otherwise, fall through and perform the addition,
// branching unconditionally to the instruction at the label "endOfMthd".
adderIL.Emit(OpCodes.Ldarg_1);
adderIL.Emit(OpCodes.Ldc_I4_S, 100);
adderIL.Emit(OpCodes.Bgt_S, failed);
adderIL.Emit(OpCodes.Ldarg_0);
adderIL.Emit(OpCodes.Ldarg_1);
adderIL.Emit(OpCodes.Add_Ovf_Un);
adderIL.Emit(OpCodes.Stloc_S, tmp1);
adderIL.Emit(OpCodes.Br_S, endOfMthd);
// If one of the arguments was greater than 100, we need to throw an
// exception. We'll use "OverflowException" with a customized message.
// First, we load our message onto the stack, and then create a new
// exception object using the constructor overload that accepts a
// string message.
adderIL.MarkLabel(failed);
adderIL.Emit(OpCodes.Ldstr, "Cannot accept values over 100 for add.");
adderIL.Emit(OpCodes.Newobj, exCtorInfo);
// We're going to need to refer to that exception object later, so let's
// store it in a temporary variable. Since the store function pops the
// the value/reference off the stack, and we'll need it to throw the
// exception, we will subsequently load it back onto the stack as well.
adderIL.Emit(OpCodes.Stloc_S, tmp2);
adderIL.Emit(OpCodes.Ldloc_S, tmp2);
// Throw the exception currently atop the stack.
adderIL.ThrowException(typeof(OverflowException));
// Start the catch block.
adderIL.BeginCatchBlock(typeof(OverflowException));
// First, we'll load a "wrapper" string, and then perform a
// late-bound call to the ToString() method of OverflowException,
// passing it the exception object we stored in local variable tmp2.
adderIL.Emit(OpCodes.Ldstr, "{0}");
adderIL.Emit(OpCodes.Ldloc_S, tmp2);
adderIL.EmitCall(OpCodes.Callvirt, exToStrMI, null);
// Now, we should have the "wrapper" string atop the stack,
// along with the string result of the ToString() call. All
// conditions are met to call WriteLine(string, object).
adderIL.EmitCall(OpCodes.Call, writeLineMI, null);
// Since our function has to return an integer value, we'll load -1 onto
// the stack to indicate an error, and store it in local variable tmp1.
adderIL.Emit(OpCodes.Ldc_I4_M1);
adderIL.Emit(OpCodes.Stloc_S, tmp1);
// End the exception handling block.
adderIL.EndExceptionBlock();
// The end of the method. If no exception was thrown, the correct value
// will be saved in tmp1. If an exception was thrown, tmp1 will be equal
// to -1. Either way, we'll load the value of tmp1 onto the stack and return.
adderIL.MarkLabel(endOfMthd);
adderIL.Emit(OpCodes.Ldloc_S, tmp1);
adderIL.Emit(OpCodes.Ret);
return myTypeBldr.CreateType();
}
public static void Main() {
Type adderType = BuildAdderType();
object addIns = Activator.CreateInstance(adderType);
object[] addParams = new object[2];
Console.Write("Enter an integer value: ");
addParams[0] = (object)Convert.ToInt32(Console.ReadLine());
Console.Write("Enter another integer value: ");
addParams[1] = (object)Convert.ToInt32(Console.ReadLine());
Console.WriteLine("If either integer was > 100, an exception will be thrown.");
Console.WriteLine("---");
Console.WriteLine("{0} + {1} = {2}",
addParams[0], addParams[1],
adderType.InvokeMember("DoAdd",
BindingFlags.InvokeMethod,
null,
addIns,
addParams));
}
}
[C++]
#using <mscorlib.dll>
using namespace System;
using namespace System::Threading;
using namespace System::Reflection;
using namespace System::Reflection::Emit;
Type* BuildAdderType() {
AppDomain* myDomain = Thread::GetDomain();
AssemblyName* myAsmName = new AssemblyName();
myAsmName->Name = S"AdderExceptionAsm";
AssemblyBuilder* myAsmBldr = myDomain->DefineDynamicAssembly(myAsmName,
AssemblyBuilderAccess::Run);
ModuleBuilder* myModBldr = myAsmBldr->DefineDynamicModule(S"AdderExceptionMod");
TypeBuilder* myTypeBldr = myModBldr->DefineType(S"Adder");
Type* adderParams[] = {__typeof(int), __typeof(int)};
// This method will add two numbers which are 100 or less. If either of the
// passed integer vales are greater than 100, it will throw an exception.
MethodBuilder* adderBldr = myTypeBldr->DefineMethod(
S"DoAdd",
static_cast<MethodAttributes>(MethodAttributes::Public | MethodAttributes::Static),
__typeof(int),
adderParams);
ILGenerator* adderIL = adderBldr->GetILGenerator();
// representing the offset IL instruction block to branch to.
// These labels, when the MarkLabel(Label) method is invoked,
// will specify the IL instruction to branch to.
Type* temp0 [] = {__typeof(String)};
ConstructorInfo* exCtorInfo = __typeof(OverflowException)->GetConstructor(temp0);
MethodInfo* exToStrMI = __typeof(OverflowException)->GetMethod(S"ToString");
Type* temp1 [] = {__typeof(String), __typeof(Object)};
MethodInfo* writeLineMI = __typeof(Console)->GetMethod(S"WriteLine",
temp1);
LocalBuilder* tmp1 = adderIL->DeclareLocal(__typeof(int));
LocalBuilder* tmp2 = adderIL->DeclareLocal(__typeof(OverflowException));
Label failed = adderIL->DefineLabel();
Label endOfMthd = adderIL->DefineLabel();
// First, load argument 0 and the integer value of S"100" onto the
// stack. If arg0 > 100, branch to the label S"failed", which is marked
// as the address of the block that throws an exception.
Label exBlock = adderIL->BeginExceptionBlock();
adderIL->Emit(OpCodes::Ldarg_0);
adderIL->Emit(OpCodes::Ldc_I4_S, 100);
adderIL->Emit(OpCodes::Bgt_S, failed);
// Now, check to see if argument 1 was greater than 100. If it was,
// branch to S"failed." Otherwise, fall through and perform the addition,
// branching unconditionally to the instruction at the label S"endOfMthd".
adderIL->Emit(OpCodes::Ldarg_1);
adderIL->Emit(OpCodes::Ldc_I4_S, 100);
adderIL->Emit(OpCodes::Bgt_S, failed);
adderIL->Emit(OpCodes::Ldarg_0);
adderIL->Emit(OpCodes::Ldarg_1);
adderIL->Emit(OpCodes::Add_Ovf_Un);
adderIL->Emit(OpCodes::Stloc_S, tmp1);
adderIL->Emit(OpCodes::Br_S, endOfMthd);
// If one of the arguments was greater than 100, we need to throw an
// exception. We'll use "OverflowException" with a customized message.
// First, we load our message onto the stack, and then create a new
// exception Object using the constructor overload that accepts a
// String* message.
adderIL->MarkLabel(failed);
adderIL->Emit(OpCodes::Ldstr, S"Cannot accept values over 100 for add.");
adderIL->Emit(OpCodes::Newobj, exCtorInfo);
// We're going to need to refer to that exception Object later, so let's
// store it in a temporary variable. Since the store function pops the
// the value/reference off the stack, and we'll need it to throw the
// exception, we will subsequently load it back onto the stack as well.
adderIL->Emit(OpCodes::Stloc_S, tmp2);
adderIL->Emit(OpCodes::Ldloc_S, tmp2);
// Throw the exception currently atop the stack.
adderIL->ThrowException(__typeof(OverflowException));
// Start the catch block.
adderIL->BeginCatchBlock(__typeof(OverflowException));
// First, we'll load a "wrapper" String, and then perform a
// late-bound call to the ToString() method of OverflowException,
// passing it the exception Object we stored in local variable tmp2.
adderIL->Emit(OpCodes::Ldstr, S" {0}");
adderIL->Emit(OpCodes::Ldloc_S, tmp2);
adderIL->EmitCall(OpCodes::Callvirt, exToStrMI, 0);
// Now, we should have the "wrapper" String atop the stack,
// along with the String result of the ToString() call. All
// conditions are met to call WriteLine(String*, Object*).
adderIL->EmitCall(OpCodes::Call, writeLineMI, 0);
// Since our function has to return an integer value, we'll load -1 onto
// the stack to indicate an error, and store it in local variable tmp1.
adderIL->Emit(OpCodes::Ldc_I4_M1);
adderIL->Emit(OpCodes::Stloc_S, tmp1);
// End the exception handling block.
adderIL->EndExceptionBlock();
// The end of the method. If no exception was thrown, the correct value
// will be saved in tmp1. If an exception was thrown, tmp1 will be equal
// to -1. Either way, we'll load the value of tmp1 onto the stack and return.
adderIL->MarkLabel(endOfMthd);
adderIL->Emit(OpCodes::Ldloc_S, tmp1);
adderIL->Emit(OpCodes::Ret);
return myTypeBldr->CreateType();
}
int main() {
Type* adderType = BuildAdderType();
Object* addIns = Activator::CreateInstance(adderType);
Object* addParams[] = new Object*[2];
Console::Write(S"Enter an integer value: ");
addParams[0] = __box(Convert::ToInt32(Console::ReadLine()));
Console::Write(S"Enter another integer value: ");
addParams[1] = __box(Convert::ToInt32(Console::ReadLine()));
Console::WriteLine(S"If either integer was > 100, an exception will be thrown.");
Console::WriteLine(S"---");
Console::WriteLine(S" {0} + {1} = {2}",
addParams[0], addParams[1],
adderType->InvokeMember(S"DoAdd",
BindingFlags::InvokeMethod,
0,
addIns,
addParams));
}
[JScript] JScript のサンプルはありません。Visual Basic、C#、および C++ のサンプルを表示するには、このページの左上隅にある言語のフィルタ ボタン をクリックします。
必要条件
プラットフォーム: Windows 98, Windows NT 4.0, Windows Millennium Edition, Windows 2000, Windows XP Home Edition, Windows XP Professional, Windows Server 2003 ファミリ
参照
ILGenerator クラス | ILGenerator メンバ | System.Reflection.Emit 名前空間