停用的執行時間封送處理
當屬性 System.Runtime.CompilerServices.DisableRuntimeMarshallingAttribute
套用至元件時,執行時間會停用 Managed 與原生表示之間的資料封送處理最內建支援。 本文說明停用的功能,以及 .NET 類型在封送處理停用時如何對應至原生類型。
封送處理已停用的案例
DisableRuntimeMarshallingAttribute
當 套用至元件時,它會影響元件中的 P/Invokes 和 Delegate 類型,以及元件中 Unmanaged 函式指標的任何呼叫。 它不會影響其他元件中定義的任何 P/Invoke 或 Interop 委派類型。 它也不會停用執行時間內建 COM Interop 支援的封送處理。 您可以透過 功能參數來啟用或停用內建 COM Interop 支援。
停用的功能
DisableRuntimeMarshallingAttribute
當 套用至元件時,下列屬性將不會有任何作用或擲回例外狀況:
- LCIDConversionAttribute 在 P/Invoke 或委派上
SetLastError=true
在 P/Invoke 上ThrowOnUnmappableChar=true
在 P/Invoke 上BestFitMapping=true
在 P/Invoke 上- .NET variadic 引數方法簽章 (varargs)
in
、 、ref
out
參數
對常見類型進行封送處理的預設規則
停用封送處理時,預設封送處理的規則會變更為更簡單的規則。 以下說明這些規則。 如 Interop 最佳做法檔中所述,Blittable 類型是 Managed 和機器碼中具有相同版面配置的類型,因此不需要任何封送處理。 此外,這些規則不能使用自訂 參數封送處理檔中所述的工具進行自訂。
C# 關鍵字 | .NET 類型 | 原生類型 |
---|---|---|
byte |
System.Byte |
uint8_t |
sbyte |
System.SByte |
int8_t |
short |
System.Int16 |
int16_t |
ushort |
System.UInt16 |
uint16_t |
int |
System.Int32 |
int32_t |
uint |
System.UInt32 |
uint32_t |
long |
System.Int64 |
int64_t |
ulong |
System.UInt64 |
uint64_t |
char |
System.Char |
char16_t P/Invoke 上的 (CharSet 沒有任何作用) |
nint |
System.IntPtr |
intptr_t |
nuint |
System.UIntPtr |
uintptr_t |
System.Boolean |
bool |
|
無欄位的使用者定義C# unmanaged 類型LayoutKind.Auto |
視為 Blittable 類型。 會忽略所有 自訂結構封送 處理。 | |
所有其他類型 | 不支援 |
範例
下列範例顯示停用執行時間封送處理時啟用或停用的一些功能:
using System.Runtime.InteropServices;
struct Unmanaged
{
int i;
}
[StructLayout(LayoutKind.Auto)]
struct AutoLayout
{
int i;
}
struct StructWithAutoLayoutField
{
AutoLayout f;
}
[UnmanagedFunctionPointer] // OK: UnmanagedFunctionPointer attribute is supported
public delegate void Callback();
[UnmanagedFunctionPointer(CallingConvention.Cdecl)] // OK: Specifying a calling convention is supported
public delegate void Callback2(int i); // OK: primitive value types are allowed
[DllImport("NativeLibrary", EntryPoint = "CustomEntryPointName")] // OK: Specifying a custom entry-point name is supported
public static extern void Import(int i);
[DllImport("NativeLibrary", CallingConvention = CallingConvention.Cdecl)] // OK: Specifying a custom calling convention is supported
public static extern void Import(int i);
[UnmanagedCallConv(new[] { typeof(CallConvCdecl) })] // OK: Specifying a custom calling convention is supported
[DllImport("NativeLibrary")]
public static extern void Import(int i);
[DllImport("NativeLibrary", EntryPoint = "CustomEntryPointName", CharSet = CharSet.Unicode, ExactSpelling = false)] // OK: Specifying a custom entry-point name and using CharSet-based lookup is supported
public static extern void Import(int i);
[DllImport("NativeLibrary")] // OK: Not explicitly specifying an entry-point name is supported
public static extern void Import(Unmanaged u); // OK: unmanaged type
[DllImport("NativeLibrary")] // OK: Not explicitly specifying an entry-point name is supported
public static extern void Import(StructWithAutoLayoutField u); // Error: unmanaged type with auto-layout field
[DllImport("NativeLibrary")]
public static extern void Import(Callback callback); // Error: managed types are not supported when runtime marshalling is disabled