2014-05-22 36 views
1

如何返回MIB_IPFORWARDROW數組?如何獲得從C到C#的結構中的非託管可變長度C數組?

struct MIB_IPFORWARDTABLE 
{ 
    public uint Size; 

    [MarshalAs(/* what goes here? */)] 
    public IPFORWARDROW[] Table; 
}; 

[DllImport("iphlpapi", CharSet = CharSet.Auto)] 
private static extern int GetIpForwardTable(
    IntPtr /* MIB_IPFORWARDTABLE* */ pIpForwardTable, 
    ref uint /* ULONG* */ pdwSize, 
    bool bOrder); 

public static MIB_IPFORWARDROW[] Temp() 
{ 
    var fwdTable = IntPtr.Zero; 
    uint size = 0; 
    var result = GetIpForwardTable(fwdTable, ref size, true); 
    fwdTable = Marshal.AllocHGlobal((int) size); 
    result = GetIpForwardTable(fwdTable, ref size, true); 

    /* 
    what now ? 
    I tried: 

    var table = (MIB_IPFORWARDTABLE) Marshal.PtrToStructure(fwdTable, typeof(MIB_IPFORWARDTABLE)); 

    but table.Table is always null 
    */ 
} 

(見GetIpForwardTable

我已經看到了這一點: How do I marshal a struct that contains a variable-sized array to C#?

但無論我做什麼,fwdTable.Table始終爲空,IntPtr.Zero或0.也就是說ofcourse,如果不會引發任何異常..

+0

檢查此:http://stackoverflow.com/questions/162897/marshal-char-in-c-sharp –

+0

@MichaelKniffen - 不要我」 t看看它是如何相關的 – Tar

回答

1

此線程似乎正是你在找什麼:http://social.msdn.microsoft.com/Forums/vstudio/en-US/19a3ce21-e395-4151-86f6-723a64272f0d/calling-getipforwardtable-from-c?forum=csharpgeneral

他們的解決方案使用強力循環將原始數組複製到IPFORWARDROW的System.Array中。

最終的代碼看起來是這樣的:

[ComVisible(false), StructLayout(LayoutKind.Sequential)] 
    internal struct IPForwardTable 
    { 
     public uint Size; 

     [MarshalAs(UnmanagedType.ByValArray, SizeConst = 1)] 
     public IPFORWARDROW[] Table; 
    }; 

    [ComVisible(false), StructLayout(LayoutKind.Sequential)] 
    internal struct IPFORWARDROW 
    { 
     internal int /*DWORD*/ dwForwardDest; 
     internal int /*DWORD*/ dwForwardMask; 
     internal int /*DWORD*/ dwForwardPolicy; 
     internal int /*DWORD*/ dwForwardNextHop; 
     internal int /*DWORD*/ dwForwardIfIndex; 
     internal int /*DWORD*/ dwForwardType; 
     internal int /*DWORD*/ dwForwardProto; 
     internal int /*DWORD*/ dwForwardAge; 
     internal int /*DWORD*/ dwForwardNextHopAS; 
     internal int /*DWORD*/ dwForwardMetric1; 
     internal int /*DWORD*/ dwForwardMetric2; 
     internal int /*DWORD*/ dwForwardMetric3; 
     internal int /*DWORD*/ dwForwardMetric4; 
     internal int /*DWORD*/ dwForwardMetric5; 
    }; 

    [DllImport("iphlpapi", CharSet = CharSet.Auto)] 
    private extern static int GetIpForwardTable(IntPtr /*PMIB_IPFORWARDTABLE*/ pIpForwardTable, ref int /*PULONG*/ pdwSize, bool bOrder); 

    [DllImport("iphlpapi", CharSet = CharSet.Auto)] 
    private extern static int CreateIpForwardEntry(IntPtr /*PMIB_IPFORWARDROW*/ pRoute); 

    static void Main(string[] args) 
    { 
     var fwdTable = IntPtr.Zero; 
     int size = 0; 

     var result = GetIpForwardTable(fwdTable, ref size, true); 
     fwdTable = Marshal.AllocHGlobal(size); 

     result = GetIpForwardTable(fwdTable, ref size, true); 
     var str = (IPForwardTable)Marshal.PtrToStructure(fwdTable, typeof(IPForwardTable)); 

     IPFORWARDROW[] table = new IPFORWARDROW[str.Size]; 
     IntPtr p = fwdTable + Marshal.SizeOf(str.Size); 
     for (int i = 0; i < str.Size; ++i) 
     { 
      table[i] = (IPFORWARDROW)Marshal.PtrToStructure(p, typeof(IPFORWARDROW)); 
      p += Marshal.SizeOf(typeof(IPFORWARDROW)); 
     } 


     Marshal.FreeHGlobal(fwdTable); 
    } 
+0

'var str =(IPForwardTable)Marshal.PtrToStructure(fwdTable,typeof(IPForwardTable));'拋出'NullReferenceException' – Tar

+0

oops。清理代碼,我刪除了一些重要的代碼(比如分配存儲結果所需的內存)。編輯。 –

相關問題