PInvoke的C#使用的DllImport在C#

问题描述:

C++函数头在DLL这两函数来获取关于使用赢得Mobile 6.5的设备我周围的WiFi站的一些信息C++ DLL,我需要调用它们在C#代码中使用它们PInvoke的C#使用的DllImport在C#

// (adapter names , pointer to destination buffer ,and the size , returned structs) 
bool __declspec(dllexport) GetBBSIDs(LPWSTR pAdapter, struct BSSIDInfo *pDest, DWORD &dwBufSizeBytes, DWORD &dwReturnedItems); 
bool __declspec(dllexport) RefreshBSSIDs(LPWSTR pAdapter); 
bool __declspec(dllexport) GetAdapters(LPWSTR pDest, DWORD &dwBufSizeBytes); 

C#示例

[DllImport(@"\Storage Card\Work\Beaad.dll", EntryPoint = "GetAdapters", SetLastError = true)] 
public static extern bool getAdapters([MarshalAs(UnmanagedType.LPWStr)] String buf, ref UInt32 dwBufSizeBytes); 

[DllImport(@"\Storage Card\Work\Beaad.dll", EntryPoint = "RefreshBSSIDs", SetLastError = true)] 
public static extern bool refreshBSSIDs([MarshalAs(UnmanagedType.LPWStr)]String buf); 

[DllImport(@"\Storage Card\Work\Beaad.dll", EntryPoint = "GetBBSIDs", SetLastError = true)] 
public static extern bool getBBSIDs([MarshalAs(UnmanagedType.LPWStr)]String buf,BSSIDInfo [] nfo, ref UInt32 dwBufSizeBytes, ref UInt32 dwReturnedItems); 

[StructLayout(LayoutKind.Sequential,CharSet=CharSet.Auto)] 
public struct BSSIDInfo 
{ 
    public byte[] BSSID; //mac 
    public char[] SSID; 

    public BSSIDInfo(byte[]bs,char[] ss) 
    { 
     this.RSSI = 0; 
     this.Infastructure = 0; 
     this.Channel = 0; 
     this.Auth = 0; 
     bs = new byte[6]; 
     ss = new char[32]; 
     BSSID = bs; 
     SSID = ss; 
    } 
    public int RSSI; 
    public int Channel; 
    public int Infastructure; 
    public int Auth; 
} 

public static byte[] StrToByteArray(string str) 
{ 
    System.Text.UTF8Encoding encoding = new System.Text.UTF8Encoding(); 
    return encoding.GetBytes(str); 
} 
public static char[] c = new char[1024]; 
string buf = new string(c); 
public void button1_Click(object sender, EventArgs e) 
{ 
    BSSIDInfo[] nfo = new BSSIDInfo[128]; 
    byte[] bytee=StrToByteArray(buf); 
    UInt32 dwsize= new UInt32(); 
    UInt32 dwTmp = new UInt32(); 
    UInt32 dwCount = new UInt32(); 
    dwTmp = Convert.ToUInt32(Marshal.SizeOf(typeof(BSSIDInfo)) * nfo.Length); 
    dwCount =0; 
    dwsize=Convert.ToUInt32(bytee.Length); 
    if (false == getAdapters(buf,ref dwsize) || dwsize == 0) 
    { 
     label1.Text = "no adabters"; 
    } 
    else 
    { 
     String [] strList=new String[15];  
     if (buf.Contains(',') == false)// one adapter 
     { 
      textBox1.Text = buf; 
     } 
     else 
     { 
      strList = buf.Split(','); 
      for (int i = 0; i < strList.Length; i++) 
      { 
       textBox1.Text+= strList[i]+Environment.NewLine; 
      } 
     } 
     if (refreshBSSIDs(buf) && getBBSIDs(buf, nfo, ref dwTmp, ref dwCount) && dwCount > 0) 
     { 
      //refreshBSSIDs(buf) && 
      for (int i = 0; i < dwCount; i++) 
      { 
       textBox2.Text += nfo.GetValue(i).ToString() + Environment.NewLine; 
      } 
     } 
     else 
     { 
      //make another thing 
     } 
    } 
} 

,当我把这个DLL在移动和C#APP.EXE是命名为Getadapters(..)第一回给我的适配器的名称的第一个函数textbox1则应用程序停止,并在移动设备尝试执行时给予我不支持的异常e另一个名为refreshBSSID()和getBSSIDs()的函数有什么问题?还是有另一种解决方案来获取这些信息(BSSID,SS ..等等)?

默认情况下为C++,除非更改使用调用方(Cdecl)调用约定。您的C++代码不会更改调用约定。默认情况下你的C#代码(除非你改变它)将使用被调用者约定(StdCall)。

虽然这可能不是完全问题,但它仍然是技术上不正确的。即使你要解决目前的问题,由于调用约定,你可能最终会遇到问题。

我打算猜测你的C#BSSIDInfo结构与C++结构不匹配。为什么当它是所有给定的字符串GetBytes会的方法StrToByteArray ...

当移动尝试执行 另外两个函数命名为 refreshBSSID()和getBSSIDs()等什么 是问题 ?或者是否有另一个 解决方案来获取此信息

我以为我知道原因采取了另一种看法,我错了。

+0

我会说点什么...主要是使用StrToByte函数的第一个函数执行得很好..现在问题在第二个函数中 – 2011-04-15 01:17:10