共用方式為


TypeBuilder.DefinePInvokeMethod 方法

定義

定義 PInvoke 方法。

多載

DefinePInvokeMethod(String, String, MethodAttributes, CallingConventions, Type, Type[], CallingConvention, CharSet)

定義 PInvoke 方法指定名稱、方法定義所在的 DLL 名稱、方法的屬性、方法的呼叫慣例、方法的傳回類型、方法的參數類型和 PInvoke 旗標。

DefinePInvokeMethod(String, String, String, MethodAttributes, CallingConventions, Type, Type[], CallingConvention, CharSet)

定義 PInvoke 方法指定名稱、方法定義所在的 DLL 名稱、進入點名稱、方法的屬性、方法的呼叫慣例、方法的傳回類型、方法的參數類型和 PInvoke 旗標。

DefinePInvokeMethod(String, String, String, MethodAttributes, CallingConventions, Type, Type[], Type[], Type[], Type[][], Type[][], CallingConvention, CharSet)

定義 PInvoke 方法,方法是指定其名稱、方法定義所在的 DLL 名稱、進入點名稱、方法的屬性、方法的呼叫慣例、方法的傳回類型、方法的參數類型、PInvoke 旗標和這些參數與傳回類型的自訂修飾詞。

DefinePInvokeMethod(String, String, MethodAttributes, CallingConventions, Type, Type[], CallingConvention, CharSet)

來源:
TypeBuilder.cs
來源:
TypeBuilder.cs
來源:
TypeBuilder.cs

定義 PInvoke 方法指定名稱、方法定義所在的 DLL 名稱、方法的屬性、方法的呼叫慣例、方法的傳回類型、方法的參數類型和 PInvoke 旗標。

public:
 System::Reflection::Emit::MethodBuilder ^ DefinePInvokeMethod(System::String ^ name, System::String ^ dllName, System::Reflection::MethodAttributes attributes, System::Reflection::CallingConventions callingConvention, Type ^ returnType, cli::array <Type ^> ^ parameterTypes, System::Runtime::InteropServices::CallingConvention nativeCallConv, System::Runtime::InteropServices::CharSet nativeCharSet);
public System.Reflection.Emit.MethodBuilder DefinePInvokeMethod (string name, string dllName, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, Type? returnType, Type[]? parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet);
public System.Reflection.Emit.MethodBuilder DefinePInvokeMethod (string name, string dllName, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, Type returnType, Type[] parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet);
member this.DefinePInvokeMethod : string * string * System.Reflection.MethodAttributes * System.Reflection.CallingConventions * Type * Type[] * System.Runtime.InteropServices.CallingConvention * System.Runtime.InteropServices.CharSet -> System.Reflection.Emit.MethodBuilder
Public Function DefinePInvokeMethod (name As String, dllName As String, attributes As MethodAttributes, callingConvention As CallingConventions, returnType As Type, parameterTypes As Type(), nativeCallConv As CallingConvention, nativeCharSet As CharSet) As MethodBuilder

參數

name
String

PInvoke 方法的名稱。 name 不能包含內嵌的 null。

dllName
String

PInvoke 方法定義所在的 DLL 名稱。

attributes
MethodAttributes

方法的屬性。

callingConvention
CallingConventions

方法的呼叫慣例。

returnType
Type

方法的傳回類型。

parameterTypes
Type[]

方法參數的類型。

nativeCallConv
CallingConvention

原生呼叫慣例。

nativeCharSet
CharSet

方法的原生字元集。

傳回

已定義的 PInvoke 方法。

例外狀況

這個方法不是靜態的。

-或-

父類型是介面。

-或-

這是抽象方法。

-或-

方法之前已定義過。

-或-

namedllName 的長度為零。

namedllNamenull

之前已使用 CreateType() 建立包含類型。

範例

下列範例示範如何使用 DefinePInvokeMethod 方法來建立 PInvoke 方法,以及如何使用 和 MethodBuilder.SetImplementationFlags 方法,將旗標新增MethodImplAttributes.PreserveSig至 方法實作旗MethodBuilderMethodBuilder.GetMethodImplementationFlags標。

重要

若要取得非零的傳回值,您必須新增 MethodImplAttributes.PreserveSig 旗標。

此範例會建立具有一個動態模組的動態元件,以及包含 PInvoke 方法的單一類型MyType。 方法 PInvoke 代表 Win32 GetTickCount 函式。

執行範例時,它會執行 PInvoke 方法。 它也會將動態元件儲存為 PInvokeTest.dll。 您可以使用 Ildasm.exe (IL 反組譯程式) 來檢查MyType類別及其static包含之 Visual Basic) PInvoke 方法中的 (Shared。 您可以在執行 csc.exe 或 vbc.exe 時,包含 DLL 的參考,以編譯使用靜態MyType.GetTickCount方法的 Visual Basic 或 C# 程式,例如 。 /r:PInvokeTest.dll

using namespace System;
using namespace System::Text;
using namespace System::Reflection;
using namespace System::Reflection::Emit;
using namespace System::Runtime::InteropServices;

    void main()
    {
        // Create the AssemblyBuilder.
        AssemblyName^ asmName = gcnew AssemblyName("PInvokeTest");
        AssemblyBuilder^ dynamicAsm = AppDomain::CurrentDomain->DefineDynamicAssembly(
            asmName, 
            AssemblyBuilderAccess::RunAndSave
        );

        // Create the module.
        ModuleBuilder^ dynamicMod = 
            dynamicAsm->DefineDynamicModule(asmName->Name, asmName->Name + ".dll");

        // Create the TypeBuilder for the class that will contain the 
        // signature for the PInvoke call.
        TypeBuilder^ tb = dynamicMod->DefineType(
            "MyType", 
            TypeAttributes::Public | TypeAttributes::UnicodeClass
        );
    
        MethodBuilder^ mb = tb->DefinePInvokeMethod(
            "GetTickCount",
            "Kernel32.dll",
            MethodAttributes::Public | MethodAttributes::Static | MethodAttributes::PinvokeImpl,
            CallingConventions::Standard,
            int::typeid,
            Type::EmptyTypes,
            CallingConvention::Winapi,
            CharSet::Ansi);

        // Add PreserveSig to the method implementation flags. NOTE: If this line
        // is commented out, the return value will be zero when the method is
        // invoked.
        mb->SetImplementationFlags(
            mb->GetMethodImplementationFlags() | MethodImplAttributes::PreserveSig);

        // The PInvoke method does not have a method body. 

        // Create the class and test the method.
        Type^ t = tb->CreateType();

        MethodInfo^ mi = t->GetMethod("GetTickCount");
        Console::WriteLine("Testing PInvoke method...");
        Console::WriteLine("GetTickCount returned: {0}", mi->Invoke(nullptr, nullptr));

        // Produce the .dll file.
        Console::WriteLine("Saving: " + asmName->Name + ".dll");
        dynamicAsm->Save(asmName->Name + ".dll");
    };

/* This example produces output similar to the following:

Testing PInvoke method...
GetTickCount returned: 1314410994
Saving: PInvokeTest.dll
 */
using System;
using System.Text;
using System.Reflection;
using System.Reflection.Emit;
using System.Runtime.InteropServices;

public class Example
{
    public static void Main()
    {
        // Create the AssemblyBuilder.
        AssemblyName asmName = new AssemblyName("PInvokeTest");
        AssemblyBuilder dynamicAsm = AppDomain.CurrentDomain.DefineDynamicAssembly(
            asmName,
            AssemblyBuilderAccess.RunAndSave
        );

        // Create the module.
        ModuleBuilder dynamicMod =
            dynamicAsm.DefineDynamicModule(asmName.Name, asmName.Name + ".dll");

        // Create the TypeBuilder for the class that will contain the
        // signature for the PInvoke call.
        TypeBuilder tb = dynamicMod.DefineType(
            "MyType",
            TypeAttributes.Public | TypeAttributes.UnicodeClass
        );

        MethodBuilder mb = tb.DefinePInvokeMethod(
            "GetTickCount",
            "Kernel32.dll",
            MethodAttributes.Public | MethodAttributes.Static | MethodAttributes.PinvokeImpl,
            CallingConventions.Standard,
            typeof(int),
            Type.EmptyTypes,
            CallingConvention.Winapi,
            CharSet.Ansi);

        // Add PreserveSig to the method implementation flags. NOTE: If this line
        // is commented out, the return value will be zero when the method is
        // invoked.
        mb.SetImplementationFlags(
            mb.GetMethodImplementationFlags() | MethodImplAttributes.PreserveSig);

        // The PInvoke method does not have a method body.

        // Create the class and test the method.
        Type t = tb.CreateType();

        MethodInfo mi = t.GetMethod("GetTickCount");
        Console.WriteLine("Testing PInvoke method...");
        Console.WriteLine("GetTickCount returned: {0}", mi.Invoke(null, null));

        // Produce the .dll file.
        Console.WriteLine("Saving: " + asmName.Name + ".dll");
        dynamicAsm.Save(asmName.Name + ".dll");
    }
}

/* This example produces output similar to the following:

Testing PInvoke method...
GetTickCount returned: 1312576235
Saving: PInvokeTest.dll
 */
Imports System.Text
Imports System.Reflection
Imports System.Reflection.Emit
Imports System.Runtime.InteropServices

Public Class Example
    
    Public Shared Sub Main() 
        
        ' Create the AssemblyBuilder.
        Dim asmName As New AssemblyName("PInvokeTest")
        Dim dynamicAsm As AssemblyBuilder = _
            AppDomain.CurrentDomain.DefineDynamicAssembly(asmName, _
                AssemblyBuilderAccess.RunAndSave)
        
        ' Create the module.
        Dim dynamicMod As ModuleBuilder = _
            dynamicAsm.DefineDynamicModule(asmName.Name, asmName.Name & ".dll")
        
        ' Create the TypeBuilder for the class that will contain the 
        ' signature for the PInvoke call.
        Dim tb As TypeBuilder = dynamicMod.DefineType("MyType", _
            TypeAttributes.Public Or TypeAttributes.UnicodeClass)
        
        Dim mb As MethodBuilder = tb.DefinePInvokeMethod( _
            "GetTickCount", _
            "Kernel32.dll", _
            MethodAttributes.Public Or MethodAttributes.Static Or MethodAttributes.PinvokeImpl, _
            CallingConventions.Standard, _
            GetType(Integer), _
            Type.EmptyTypes, _
            CallingConvention.Winapi, _
            CharSet.Ansi)

        ' Add PreserveSig to the method implementation flags. NOTE: If this line
        ' is commented out, the return value will be zero when the method is
        ' invoked.
        mb.SetImplementationFlags( _
            mb.GetMethodImplementationFlags() Or MethodImplAttributes.PreserveSig)
        
        ' The PInvoke method does not have a method body.
        
        ' Create the class and test the method.
        Dim t As Type = tb.CreateType()

        Dim mi As MethodInfo = t.GetMethod("GetTickCount")
        Console.WriteLine("Testing PInvoke method...")
        Console.WriteLine("GetTickCount returned: {0}", mi.Invoke(Nothing, Nothing))

        ' Produce the .dll file.
        Console.WriteLine("Saving: " & asmName.Name & ".dll")
        dynamicAsm.Save(asmName.Name & ".dll")
    
    End Sub  
End Class 

' This example produces output similar to the following:
'
'Testing PInvoke method...
'GetTickCount returned: 1313078714
'Saving: PInvokeTest.dll

備註

某些 DLL 匯入屬性 (看到無法將) 的描述指定為這個方法的 DllImportAttribute 自變數。 例如,如果方法傳回值,則必須在建立 方法之後PInvoke加入 DLL 匯入屬性MethodImplAttributes.PreserveSig。 此範例示範如何執行這項操作。

適用於

DefinePInvokeMethod(String, String, String, MethodAttributes, CallingConventions, Type, Type[], CallingConvention, CharSet)

來源:
TypeBuilder.cs
來源:
TypeBuilder.cs
來源:
TypeBuilder.cs

定義 PInvoke 方法指定名稱、方法定義所在的 DLL 名稱、進入點名稱、方法的屬性、方法的呼叫慣例、方法的傳回類型、方法的參數類型和 PInvoke 旗標。

public:
 System::Reflection::Emit::MethodBuilder ^ DefinePInvokeMethod(System::String ^ name, System::String ^ dllName, System::String ^ entryName, System::Reflection::MethodAttributes attributes, System::Reflection::CallingConventions callingConvention, Type ^ returnType, cli::array <Type ^> ^ parameterTypes, System::Runtime::InteropServices::CallingConvention nativeCallConv, System::Runtime::InteropServices::CharSet nativeCharSet);
public System.Reflection.Emit.MethodBuilder DefinePInvokeMethod (string name, string dllName, string entryName, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, Type? returnType, Type[]? parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet);
public System.Reflection.Emit.MethodBuilder DefinePInvokeMethod (string name, string dllName, string entryName, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, Type returnType, Type[] parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet);
member this.DefinePInvokeMethod : string * string * string * System.Reflection.MethodAttributes * System.Reflection.CallingConventions * Type * Type[] * System.Runtime.InteropServices.CallingConvention * System.Runtime.InteropServices.CharSet -> System.Reflection.Emit.MethodBuilder
Public Function DefinePInvokeMethod (name As String, dllName As String, entryName As String, attributes As MethodAttributes, callingConvention As CallingConventions, returnType As Type, parameterTypes As Type(), nativeCallConv As CallingConvention, nativeCharSet As CharSet) As MethodBuilder

參數

name
String

PInvoke 方法的名稱。 name 不能包含內嵌的 null。

dllName
String

PInvoke 方法定義所在的 DLL 名稱。

entryName
String

DLL 中的進入點名稱。

attributes
MethodAttributes

方法的屬性。

callingConvention
CallingConventions

方法的呼叫慣例。

returnType
Type

方法的傳回類型。

parameterTypes
Type[]

方法參數的類型。

nativeCallConv
CallingConvention

原生呼叫慣例。

nativeCharSet
CharSet

方法的原生字元集。

傳回

已定義的 PInvoke 方法。

例外狀況

這個方法不是靜態的。

-或-

父類型是介面。

-或-

這是抽象方法。

-或-

方法之前已定義過。

-或-

namedllNameentryName 的長度為零。

name dllNameentryNamenull

之前已使用 CreateType() 建立包含類型。

範例

下列程式代碼範例示範如何使用 DefinePInvokeMethod 方法來建立 PInvoke 方法,以及如何使用 和 MethodBuilder.SetImplementationFlags 方法,將旗標新增MethodImplAttributes.PreserveSig至 方法實作旗MethodBuilderMethodBuilder.GetMethodImplementationFlags標。

重要

若要取得非零的傳回值,您必須新增 MethodImplAttributes.PreserveSig 旗標。

此範例會建立具有一個動態模組的動態元件,以及包含 PInvoke 方法的單一類型MyType。 方法 PInvoke 代表 Win32 GetTickCount 函式。

執行範例時,它會執行 PInvoke 方法。 它也會將動態元件儲存為 PInvokeTest.dll。 您可以使用 Ildasm.exe (IL 反組譯程式) 來檢查MyType類別及其static包含之 Visual Basic) PInvoke 方法中的 (Shared。 您可以在執行 csc.exe 或 vbc.exe 時,包含 DLL 的參考,以編譯使用靜態MyType.GetTickCount方法的 Visual Basic 或 C# 程式,例如 。 /r:PInvokeTest.dll

using namespace System;
using namespace System::Text;
using namespace System::Reflection;
using namespace System::Reflection::Emit;
using namespace System::Runtime::InteropServices;

    void main()
    {
        // Create the AssemblyBuilder.
        AssemblyName^ asmName = gcnew AssemblyName("PInvokeTest");
        AssemblyBuilder^ dynamicAsm = AppDomain::CurrentDomain->DefineDynamicAssembly(
            asmName, 
            AssemblyBuilderAccess::RunAndSave
        );

        // Create the module.
        ModuleBuilder^ dynamicMod = 
            dynamicAsm->DefineDynamicModule(asmName->Name, asmName->Name + ".dll");

        // Create the TypeBuilder for the class that will contain the 
        // signature for the PInvoke call.
        TypeBuilder^ tb = dynamicMod->DefineType(
            "MyType", 
            TypeAttributes::Public | TypeAttributes::UnicodeClass
        );
    
        MethodBuilder^ mb = tb->DefinePInvokeMethod(
            "GetTickCount",
            "Kernel32.dll",
            MethodAttributes::Public | MethodAttributes::Static | MethodAttributes::PinvokeImpl,
            CallingConventions::Standard,
            int::typeid,
            Type::EmptyTypes,
            CallingConvention::Winapi,
            CharSet::Ansi);

        // Add PreserveSig to the method implementation flags. NOTE: If this line
        // is commented out, the return value will be zero when the method is
        // invoked.
        mb->SetImplementationFlags(
            mb->GetMethodImplementationFlags() | MethodImplAttributes::PreserveSig);

        // The PInvoke method does not have a method body. 

        // Create the class and test the method.
        Type^ t = tb->CreateType();

        MethodInfo^ mi = t->GetMethod("GetTickCount");
        Console::WriteLine("Testing PInvoke method...");
        Console::WriteLine("GetTickCount returned: {0}", mi->Invoke(nullptr, nullptr));

        // Produce the .dll file.
        Console::WriteLine("Saving: " + asmName->Name + ".dll");
        dynamicAsm->Save(asmName->Name + ".dll");
    };

/* This example produces output similar to the following:

Testing PInvoke method...
GetTickCount returned: 1314410994
Saving: PInvokeTest.dll
 */
using System;
using System.Text;
using System.Reflection;
using System.Reflection.Emit;
using System.Runtime.InteropServices;

public class Example
{
    public static void Main()
    {
        // Create the AssemblyBuilder.
        AssemblyName asmName = new AssemblyName("PInvokeTest");
        AssemblyBuilder dynamicAsm = AppDomain.CurrentDomain.DefineDynamicAssembly(
            asmName,
            AssemblyBuilderAccess.RunAndSave
        );

        // Create the module.
        ModuleBuilder dynamicMod =
            dynamicAsm.DefineDynamicModule(asmName.Name, asmName.Name + ".dll");

        // Create the TypeBuilder for the class that will contain the
        // signature for the PInvoke call.
        TypeBuilder tb = dynamicMod.DefineType(
            "MyType",
            TypeAttributes.Public | TypeAttributes.UnicodeClass
        );

        MethodBuilder mb = tb.DefinePInvokeMethod(
            "GetTickCount",
            "Kernel32.dll",
            MethodAttributes.Public | MethodAttributes.Static | MethodAttributes.PinvokeImpl,
            CallingConventions.Standard,
            typeof(int),
            Type.EmptyTypes,
            CallingConvention.Winapi,
            CharSet.Ansi);

        // Add PreserveSig to the method implementation flags. NOTE: If this line
        // is commented out, the return value will be zero when the method is
        // invoked.
        mb.SetImplementationFlags(
            mb.GetMethodImplementationFlags() | MethodImplAttributes.PreserveSig);

        // The PInvoke method does not have a method body.

        // Create the class and test the method.
        Type t = tb.CreateType();

        MethodInfo mi = t.GetMethod("GetTickCount");
        Console.WriteLine("Testing PInvoke method...");
        Console.WriteLine("GetTickCount returned: {0}", mi.Invoke(null, null));

        // Produce the .dll file.
        Console.WriteLine("Saving: " + asmName.Name + ".dll");
        dynamicAsm.Save(asmName.Name + ".dll");
    }
}

/* This example produces output similar to the following:

Testing PInvoke method...
GetTickCount returned: 1312576235
Saving: PInvokeTest.dll
 */
Imports System.Text
Imports System.Reflection
Imports System.Reflection.Emit
Imports System.Runtime.InteropServices

Public Class Example
    
    Public Shared Sub Main() 
        
        ' Create the AssemblyBuilder.
        Dim asmName As New AssemblyName("PInvokeTest")
        Dim dynamicAsm As AssemblyBuilder = _
            AppDomain.CurrentDomain.DefineDynamicAssembly(asmName, _
                AssemblyBuilderAccess.RunAndSave)
        
        ' Create the module.
        Dim dynamicMod As ModuleBuilder = _
            dynamicAsm.DefineDynamicModule(asmName.Name, asmName.Name & ".dll")
        
        ' Create the TypeBuilder for the class that will contain the 
        ' signature for the PInvoke call.
        Dim tb As TypeBuilder = dynamicMod.DefineType("MyType", _
            TypeAttributes.Public Or TypeAttributes.UnicodeClass)
        
        Dim mb As MethodBuilder = tb.DefinePInvokeMethod( _
            "GetTickCount", _
            "Kernel32.dll", _
            MethodAttributes.Public Or MethodAttributes.Static Or MethodAttributes.PinvokeImpl, _
            CallingConventions.Standard, _
            GetType(Integer), _
            Type.EmptyTypes, _
            CallingConvention.Winapi, _
            CharSet.Ansi)

        ' Add PreserveSig to the method implementation flags. NOTE: If this line
        ' is commented out, the return value will be zero when the method is
        ' invoked.
        mb.SetImplementationFlags( _
            mb.GetMethodImplementationFlags() Or MethodImplAttributes.PreserveSig)
        
        ' The PInvoke method does not have a method body.
        
        ' Create the class and test the method.
        Dim t As Type = tb.CreateType()

        Dim mi As MethodInfo = t.GetMethod("GetTickCount")
        Console.WriteLine("Testing PInvoke method...")
        Console.WriteLine("GetTickCount returned: {0}", mi.Invoke(Nothing, Nothing))

        ' Produce the .dll file.
        Console.WriteLine("Saving: " & asmName.Name & ".dll")
        dynamicAsm.Save(asmName.Name & ".dll")
    
    End Sub  
End Class 

' This example produces output similar to the following:
'
'Testing PInvoke method...
'GetTickCount returned: 1313078714
'Saving: PInvokeTest.dll

備註

某些 DLL 匯入屬性 (看到無法將) 的描述指定為這個方法的 DllImportAttribute 自變數。 例如,如果方法傳回值,則必須在建立 方法之後PInvoke加入 DLL 匯入屬性MethodImplAttributes.PreserveSig。 此範例示範如何執行這項操作。

適用於

DefinePInvokeMethod(String, String, String, MethodAttributes, CallingConventions, Type, Type[], Type[], Type[], Type[][], Type[][], CallingConvention, CharSet)

來源:
TypeBuilder.cs
來源:
TypeBuilder.cs
來源:
TypeBuilder.cs

定義 PInvoke 方法,方法是指定其名稱、方法定義所在的 DLL 名稱、進入點名稱、方法的屬性、方法的呼叫慣例、方法的傳回類型、方法的參數類型、PInvoke 旗標和這些參數與傳回類型的自訂修飾詞。

public:
 System::Reflection::Emit::MethodBuilder ^ DefinePInvokeMethod(System::String ^ name, System::String ^ dllName, System::String ^ entryName, System::Reflection::MethodAttributes attributes, System::Reflection::CallingConventions callingConvention, Type ^ returnType, cli::array <Type ^> ^ returnTypeRequiredCustomModifiers, cli::array <Type ^> ^ returnTypeOptionalCustomModifiers, cli::array <Type ^> ^ parameterTypes, cli::array <cli::array <Type ^> ^> ^ parameterTypeRequiredCustomModifiers, cli::array <cli::array <Type ^> ^> ^ parameterTypeOptionalCustomModifiers, System::Runtime::InteropServices::CallingConvention nativeCallConv, System::Runtime::InteropServices::CharSet nativeCharSet);
public System.Reflection.Emit.MethodBuilder DefinePInvokeMethod (string name, string dllName, string entryName, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, Type? returnType, Type[]? returnTypeRequiredCustomModifiers, Type[]? returnTypeOptionalCustomModifiers, Type[]? parameterTypes, Type[][]? parameterTypeRequiredCustomModifiers, Type[][]? parameterTypeOptionalCustomModifiers, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet);
public System.Reflection.Emit.MethodBuilder DefinePInvokeMethod (string name, string dllName, string entryName, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, Type returnType, Type[] returnTypeRequiredCustomModifiers, Type[] returnTypeOptionalCustomModifiers, Type[] parameterTypes, Type[][] parameterTypeRequiredCustomModifiers, Type[][] parameterTypeOptionalCustomModifiers, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet);
member this.DefinePInvokeMethod : string * string * string * System.Reflection.MethodAttributes * System.Reflection.CallingConventions * Type * Type[] * Type[] * Type[] * Type[][] * Type[][] * System.Runtime.InteropServices.CallingConvention * System.Runtime.InteropServices.CharSet -> System.Reflection.Emit.MethodBuilder
Public Function DefinePInvokeMethod (name As String, dllName As String, entryName As String, attributes As MethodAttributes, callingConvention As CallingConventions, returnType As Type, returnTypeRequiredCustomModifiers As Type(), returnTypeOptionalCustomModifiers As Type(), parameterTypes As Type(), parameterTypeRequiredCustomModifiers As Type()(), parameterTypeOptionalCustomModifiers As Type()(), nativeCallConv As CallingConvention, nativeCharSet As CharSet) As MethodBuilder

參數

name
String

PInvoke 方法的名稱。 name 不能包含內嵌的 null。

dllName
String

PInvoke 方法定義所在的 DLL 名稱。

entryName
String

DLL 中的進入點名稱。

attributes
MethodAttributes

方法的屬性。

callingConvention
CallingConventions

方法的呼叫慣例。

returnType
Type

方法的傳回類型。

returnTypeRequiredCustomModifiers
Type[]

一種類型陣列,用來為方法的傳回類型指出必要的自訂修飾詞,例如 IsConst。 如果傳回類型沒有必要的自訂修飾詞,則指定 null

returnTypeOptionalCustomModifiers
Type[]

一種類型陣列,用來為方法的傳回類型指出選擇性自訂修飾詞,例如 IsConst。 如果傳回類型沒有選擇性的自訂修飾詞,則指定 null

parameterTypes
Type[]

方法參數的類型。

parameterTypeRequiredCustomModifiers
Type[][]

類型陣列的陣列。 每個類型陣列都代表其對應參數必要的自訂修飾詞,例如 IsConst。 如果特定的參數沒有必要的自訂修飾詞,則指定 null,而非類型陣列。 如果這些參數都沒有必要的自訂修飾詞,則指定 null,而非陣列的陣列。

parameterTypeOptionalCustomModifiers
Type[][]

類型陣列的陣列。 每個類型陣列都代表其對應參數的選擇性自訂修飾詞,例如 IsConst。 如果特定的參數沒有選擇性的自訂修飾詞,則指定 null,而非類型陣列。 如果這些參數都沒有選擇性的自訂修飾詞,則指定 null,而非陣列的陣列。

nativeCallConv
CallingConvention

原生呼叫慣例。

nativeCharSet
CharSet

方法的原生字元集。

傳回

MethodBuilder,代表定義的 PInvoke 方法。

例外狀況

這個方法不是靜態的。

-或-

父類型是介面。

-或-

這是抽象方法。

-或-

方法之前已定義過。

-或-

namedllNameentryName 的長度為零。

-或-

parameterTypeRequiredCustomModifiersparameterTypeOptionalCustomModifiers 的大小不等於 parameterTypes 的大小。

namedllNameentryNamenull

先前使用 CreateType() 建立的類型。

-或-

目前動態類型的 IsGenericType 屬性為 true,但 IsGenericTypeDefinition 屬性為 false

範例

下列程式代碼範例示範如何使用 DefinePInvokeMethod 方法來建立 PInvoke 方法,以及如何使用 和 MethodBuilder.SetImplementationFlags 方法,將旗標新增MethodImplAttributes.PreserveSig至 方法實作旗MethodBuilderMethodBuilder.GetMethodImplementationFlags標。

此範例會建立具有一個動態模組的動態元件,以及包含 PInvoke 方法的單一類型MyType。 方法 PInvoke 代表 Win32 GetTickCount 函式。

重要

若要取得非零的傳回值,您必須新增 MethodImplAttributes.PreserveSig 旗標。

注意

此範例使用未指定自定義修飾詞的多載。 若要指定自定義修飾詞,請變更範例程式代碼以改用此方法多載。

執行範例時,它會執行 PInvoke 方法。 它也會將動態元件儲存為 PInvokeTest.dll。 您可以使用 Ildasm.exe (IL 反組譯程式) 來檢查MyType類別及其static包含之 Visual Basic) PInvoke 方法中的 (Shared。 您可以在執行 csc.exe 或 vbc.exe 時,包含 DLL 的參考,以編譯使用靜態MyType.GetTickCount方法的 Visual Basic 或 C# 程式,例如 。 /r:PInvokeTest.dll

using namespace System;
using namespace System::Text;
using namespace System::Reflection;
using namespace System::Reflection::Emit;
using namespace System::Runtime::InteropServices;

    void main()
    {
        // Create the AssemblyBuilder.
        AssemblyName^ asmName = gcnew AssemblyName("PInvokeTest");
        AssemblyBuilder^ dynamicAsm = AppDomain::CurrentDomain->DefineDynamicAssembly(
            asmName, 
            AssemblyBuilderAccess::RunAndSave
        );

        // Create the module.
        ModuleBuilder^ dynamicMod = 
            dynamicAsm->DefineDynamicModule(asmName->Name, asmName->Name + ".dll");

        // Create the TypeBuilder for the class that will contain the 
        // signature for the PInvoke call.
        TypeBuilder^ tb = dynamicMod->DefineType(
            "MyType", 
            TypeAttributes::Public | TypeAttributes::UnicodeClass
        );
    
        MethodBuilder^ mb = tb->DefinePInvokeMethod(
            "GetTickCount",
            "Kernel32.dll",
            MethodAttributes::Public | MethodAttributes::Static | MethodAttributes::PinvokeImpl,
            CallingConventions::Standard,
            int::typeid,
            Type::EmptyTypes,
            CallingConvention::Winapi,
            CharSet::Ansi);

        // Add PreserveSig to the method implementation flags. NOTE: If this line
        // is commented out, the return value will be zero when the method is
        // invoked.
        mb->SetImplementationFlags(
            mb->GetMethodImplementationFlags() | MethodImplAttributes::PreserveSig);

        // The PInvoke method does not have a method body. 

        // Create the class and test the method.
        Type^ t = tb->CreateType();

        MethodInfo^ mi = t->GetMethod("GetTickCount");
        Console::WriteLine("Testing PInvoke method...");
        Console::WriteLine("GetTickCount returned: {0}", mi->Invoke(nullptr, nullptr));

        // Produce the .dll file.
        Console::WriteLine("Saving: " + asmName->Name + ".dll");
        dynamicAsm->Save(asmName->Name + ".dll");
    };

/* This example produces output similar to the following:

Testing PInvoke method...
GetTickCount returned: 1314410994
Saving: PInvokeTest.dll
 */
using System;
using System.Text;
using System.Reflection;
using System.Reflection.Emit;
using System.Runtime.InteropServices;

public class Example
{
    public static void Main()
    {
        // Create the AssemblyBuilder.
        AssemblyName asmName = new AssemblyName("PInvokeTest");
        AssemblyBuilder dynamicAsm = AppDomain.CurrentDomain.DefineDynamicAssembly(
            asmName,
            AssemblyBuilderAccess.RunAndSave
        );

        // Create the module.
        ModuleBuilder dynamicMod =
            dynamicAsm.DefineDynamicModule(asmName.Name, asmName.Name + ".dll");

        // Create the TypeBuilder for the class that will contain the
        // signature for the PInvoke call.
        TypeBuilder tb = dynamicMod.DefineType(
            "MyType",
            TypeAttributes.Public | TypeAttributes.UnicodeClass
        );

        MethodBuilder mb = tb.DefinePInvokeMethod(
            "GetTickCount",
            "Kernel32.dll",
            MethodAttributes.Public | MethodAttributes.Static | MethodAttributes.PinvokeImpl,
            CallingConventions.Standard,
            typeof(int),
            Type.EmptyTypes,
            CallingConvention.Winapi,
            CharSet.Ansi);

        // Add PreserveSig to the method implementation flags. NOTE: If this line
        // is commented out, the return value will be zero when the method is
        // invoked.
        mb.SetImplementationFlags(
            mb.GetMethodImplementationFlags() | MethodImplAttributes.PreserveSig);

        // The PInvoke method does not have a method body.

        // Create the class and test the method.
        Type t = tb.CreateType();

        MethodInfo mi = t.GetMethod("GetTickCount");
        Console.WriteLine("Testing PInvoke method...");
        Console.WriteLine("GetTickCount returned: {0}", mi.Invoke(null, null));

        // Produce the .dll file.
        Console.WriteLine("Saving: " + asmName.Name + ".dll");
        dynamicAsm.Save(asmName.Name + ".dll");
    }
}

/* This example produces output similar to the following:

Testing PInvoke method...
GetTickCount returned: 1312576235
Saving: PInvokeTest.dll
 */
Imports System.Text
Imports System.Reflection
Imports System.Reflection.Emit
Imports System.Runtime.InteropServices

Public Class Example
    
    Public Shared Sub Main() 
        
        ' Create the AssemblyBuilder.
        Dim asmName As New AssemblyName("PInvokeTest")
        Dim dynamicAsm As AssemblyBuilder = _
            AppDomain.CurrentDomain.DefineDynamicAssembly(asmName, _
                AssemblyBuilderAccess.RunAndSave)
        
        ' Create the module.
        Dim dynamicMod As ModuleBuilder = _
            dynamicAsm.DefineDynamicModule(asmName.Name, asmName.Name & ".dll")
        
        ' Create the TypeBuilder for the class that will contain the 
        ' signature for the PInvoke call.
        Dim tb As TypeBuilder = dynamicMod.DefineType("MyType", _
            TypeAttributes.Public Or TypeAttributes.UnicodeClass)
        
        Dim mb As MethodBuilder = tb.DefinePInvokeMethod( _
            "GetTickCount", _
            "Kernel32.dll", _
            MethodAttributes.Public Or MethodAttributes.Static Or MethodAttributes.PinvokeImpl, _
            CallingConventions.Standard, _
            GetType(Integer), _
            Type.EmptyTypes, _
            CallingConvention.Winapi, _
            CharSet.Ansi)

        ' Add PreserveSig to the method implementation flags. NOTE: If this line
        ' is commented out, the return value will be zero when the method is
        ' invoked.
        mb.SetImplementationFlags( _
            mb.GetMethodImplementationFlags() Or MethodImplAttributes.PreserveSig)
        
        ' The PInvoke method does not have a method body.
        
        ' Create the class and test the method.
        Dim t As Type = tb.CreateType()

        Dim mi As MethodInfo = t.GetMethod("GetTickCount")
        Console.WriteLine("Testing PInvoke method...")
        Console.WriteLine("GetTickCount returned: {0}", mi.Invoke(Nothing, Nothing))

        ' Produce the .dll file.
        Console.WriteLine("Saving: " & asmName.Name & ".dll")
        dynamicAsm.Save(asmName.Name & ".dll")
    
    End Sub  
End Class 

' This example produces output similar to the following:
'
'Testing PInvoke method...
'GetTickCount returned: 1313078714
'Saving: PInvokeTest.dll

備註

某些 DLL 匯入屬性 (看到無法將) 的描述指定為這個方法的 DllImportAttribute 自變數。 例如,如果方法傳回值,則必須在建立 方法之後PInvoke加入 DLL 匯入屬性MethodImplAttributes.PreserveSig。 此範例示範如何執行這項操作。

適用於