0

DLL 中的 C++ 函数头 这两个函数使用 win mobile 6.5 设备获取有关我周围 wifi 站的一些信息,我需要调用它们以在 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 中适配器的名称,然后应用程序停止并在移动尝试执行名为 refreshBSSID() 和 getBSSIDs() 的另外两个函数,那么问题是什么?还是有其他解决方案来获取此信息(BSSID,SS ..etc)?

4

1 回答 1

0

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

虽然这可能不是您遇到的问题,但在技术上仍然不正确。即使您要解决当前的问题,您也可能最终会因为调用约定而遇到问题。

我猜你的 C# BSSIDInfo 结构与 C++ 结构不匹配。为什么 StrToByteArray 方法所做的只是给定字符串上的 GetBytes ......

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

我以为我知道原因再看一遍,我错了。

于 2011-04-14T18:39:18.910 回答