3

对于任何优秀的套接字程序员:
是否可以使用套接字通过 USB 端口枚举连接到 PC 的多个活动 IrDA 设备?
如果是这样,怎么做?这真的是我的主要问题。帖子的其余部分完善了细节并描述了我尝试过的内容。

我正在使用 Microsoft SDK 和 ANSI C 编译器在 Windows 7 上开发应用程序。应用程序设计要求它检测范围内的任何 IrDA 设备,使用套接字连接,并通过多个 IrDA 加密狗(每个设备一个加密狗)与多个设备通信,每个加密狗通过 USB 连接到 PC。注意:应避免使用虚拟 COM 端口。

我已成功使用套接字调用来枚举、创建套接字、连接并与单个 IrDA 设备通信。这很好用。
但是,我不确定如何设置代码以成功枚举多个 IrDA 设备。

到目前为止,我一次只能连接到一台设备。尽管很明显,Windows 正在发现三个 IrDA 加密狗,如下图所示 - 整体场景(第 1 图像)、设备管理器(第 2 图像)、设备属性(第 3 图像):

图 1:总体情况:
在此处输入图像描述

图 2:从设备管理器:
在此处输入图像描述

图 3:每个“找到”的 IrDA 设备的属性
(包括后两个箭头以显示所有三个设备的 Port-Hub 地址) 在此处输入图像描述

我正在使用的简单场景:(
一些变量名称与上面的场景描述不同,但在代码中是一致的)

第一个- 我将两个有源 IrDA 设备放在两个加密狗前面(相隔几英尺,因此两个设备之间没有信号模糊)现在只使用 2 个来保持简单。

第二- 我创建 2 个 IrDA 套接字,使用以下方法获取两个句柄: socket(AF_IRDA, SOCK_STREAM, 0);

第三- 我打电话:

if ((errorCode = getsockopt(gSocketHandle[0],
                 SOL_IRLMP,
                 IRLMP_ENUMDEVICES,
                 (char*)pDeviceList,
                 &deviceListLength)) == SOCKET_ERROR)  

4th - 然后我用 pDeviceList 中的新信息填充 destinIrdaDeviceAddr 和

    memcpy(&destinIrdaDeviceAddr.irdaDeviceID[0], &pDevList->Device[0].irdaDeviceID[0], 4);

5 - 调用:

connect(gSocketHandle[0],(const struct sockaddr*)&destinIrdaDeviceAddr,(int) sizeof(SOCKADDR_IRDA))

此调用完成后,我使用下一个套接字句柄(gSocketHandle 1 )重复(步骤 3 )。但是,我没有得到另一个枚举设备,而是得到了相同的设备。第二次调用会在 pDeviceList 中产生与第一个设备中相同的信息。换句话说,我只列举了一个设备。

下面是尝试枚举两个 IrDA 设备的代码:

    // adapted from http://msdn.microsoft.com/en-us/library/windows/desktop/ms691754(v=vs.85).aspx

    #include <windows.h>
    #include <winsock2.h>
    #include <ansi_c.h>
    #include <af_irda.h>

    #pragma comment(lib, "ws2_32.lib")

    #define DEVICE_LIST_LEN 5
    #define MAX_RETRIES 10

    SOCKET conn1, conn2;

    char* iGetLastErrorText(DWORD nErrorCode);

    void main()
    {
        WSADATA         wsaData;
        // discovery buffer
        BYTE          DevListBuff[sizeof(DEVICELIST) - sizeof(IRDA_DEVICE_INFO) + 
                      (sizeof(IRDA_DEVICE_INFO) * DEVICE_LIST_LEN)];
        int           DevListLen = sizeof(DevListBuff);
        PDEVICELIST   pDevList   = (PDEVICELIST) &DevListBuff;
        int           DevNum, i;

        if (WSAStartup(MAKEWORD(2,2), &wsaData) != 0)
        {
        printf("IR-Client: Unable to load the Winsock library!\n");
            getchar();
        }
        else printf("IR-Client: Winsock library 2.2 loaded!\n");

        SOCKADDR_IRDA DstAddrIR = { AF_IRDA, 0, 0, 0, 0, "IrDA:IrCOMM" };

        //Create socket handles
        if ((conn1 = socket(AF_IRDA, SOCK_STREAM, 0)) == INVALID_SOCKET)
        {
        // WSAGetLastError
        }
        if ((conn2 = socket(AF_IRDA, SOCK_STREAM, 0)) == INVALID_SOCKET)
        {
        // WSAGetLastError
        }

        /////////////////////////
        //enumerate devices - socket conn1
        /////////////////////////
        // search for the peer device
        pDevList->numDevice = 0;
        if (getsockopt(conn1, SOL_IRLMP, IRLMP_ENUMDEVICES, (CHAR *) pDevList, &DevListLen)
        == SOCKET_ERROR)
        {
        // WSAGetLastError
        }

        if (pDevList->numDevice == 0)
        {
        printf("no devices found\n");
        }

        // assume first device, we should have a common dialog here
        memcpy(&DstAddrIR.irdaDeviceID[0], &pDevList->Device[0].irdaDeviceID[0], 4);
        printf("%x\n", &DstAddrIR.irdaDeviceID[0]);


        // nothing special for IrCOMM from now on...
        if (connect(conn1, (const struct sockaddr *) &DstAddrIR, sizeof(SOCKADDR_IRDA)) 
        == SOCKET_ERROR)
        {
        // WSAGetLastError
        }

        /////////////////////////
        //enumerate devices - socket conn2
        /////////////////////////
        // search for the peer device
        pDevList->numDevice = 0;

        if (getsockopt(conn2, SOL_IRLMP, IRLMP_ENUMDEVICES, (CHAR *) pDevList, &DevListLen) == SOCKET_ERROR)
        {
        // WSAGetLastError
        }

        if (pDevList->numDevice == 0)
        {
        printf("no devices found\n");
        }

        // assume first device, we should have a common dialog here
        memcpy(&DstAddrIR.irdaDeviceID[0], &pDevList->Device[0].irdaDeviceID[0], 4);
        printf("%x\n", &DstAddrIR.irdaDeviceID[0]);

        // nothing special for IrCOMM from now on...
        if (connect(conn2, (const struct sockaddr *) &DstAddrIR, sizeof(SOCKADDR_IRDA)) 
        == SOCKET_ERROR)
        {
        // WSAGetLastError
        }
        getchar(); //to view irdaDeviceID
    }

    char* iGetLastErrorText(DWORD nErrorCode)
    {
        char* msg;
        // Ask Windows to prepare a standard message for a GetLastError() code:
        FormatMessageA(FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, NULL, nErrorCode, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPSTR)&msg, 0, NULL);
        // Return the message
        if (!msg)
        return("Unknown error");
        else
        return(msg);
    }

下图显示了 ->irdaDeviceID[0] 的值。两个值相同,表示仅枚举了一个设备。
在此处输入图像描述

4

0 回答 0