微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

将 Windows API 移植到 linux,USB HID 设备读取

如何解决将 Windows API 移植到 linux,USB HID 设备读取

我使用 USB HID 设备,一个带 LED 的按钮。现有两个 API 用于访问设备。一种用于 Windows,一种用于 linux。不幸的是,linux API 没有读取按钮状态(按下/释放)的功能,但 windows API 确实有这个功能。我想将现有功能移植到 linux API。我已经尝试了几次,但仍然无法从 USB 设备获取数据。

The existing Windows API:

The existing Linux API:

The device:

现有和功能窗口实现从设备读取的步骤:

  • 首先有一个带有id和四个字符的写操作(在要写的第一个字符中配置了0x02)

  • 然后对与之前写入相同的结构进行读取操作。读取状态的位置与之前写入时放置 0x02 的位置相同。

    PACDRIVE_API BOOL __stdcall USBButtonGetState(INT id,PBOOL state) { if(m_hidDeviceData[id].Type != DEVICETYPE_USBBUTTON) 错误

      REPORT_BUF reportBuffer;
      BOOL retVal = FALSE;
    
      reportBuffer.ReportID = 0;
      reportBuffer.ReportBuffer[0] = 0x02;
      reportBuffer.ReportBuffer[1] = 0x00;
      reportBuffer.ReportBuffer[2] = 0x00;
      reportBuffer.ReportBuffer[3] = 0x00;
    
      retVal = UsbWrite(&m_hidDeviceData[id],&reportBuffer);
    
      if(!retVal)
          return retVal;
    
      memset(&reportBuffer,sizeof(REPORT_BUF));
    
      retVal = UsbRead(&m_hidDeviceData[id],&reportBuffer);
    
      if(!retVal)
          return retVal;
    
      *state = reportBuffer.ReportBuffer[0];
    
      return retVal;
    

    }

在 linux API 中,他们使用 libusb-1.0/libusb.h 库, 现有的用于设置按钮颜色的写入函数正在使用 libusb_control_transfer 函数

bool writeUSBButton(unsigned char* barray,int autoconnect,bool transfer,unsigned int size)
{
  libusb_context *ctx = NULL;
  struct libusb_device_handle *handle = NULL;
  unsigned char mesg[USBBTN_MESG_LENGTH] = {0,0};

  bool result = true;

  int pos = 0;
  int ret = 0;

  if (transfer)
  {
    handle = openUSB(ctx,USBBTN_vendOR,USBBTN_PRODUCT,USBBTN_INTERFACE,autoconnect);

    if (!handle)
    {
      result = false;
      goto error;
    }
  }

  while (pos < size)
  {
    memcpy(&mesg[0],&barray[pos],4);

    debug ("Writing (%i): %x,%x,%x",pos,mesg[0],mesg[1],mesg[2],mesg[3]);
    if (transfer)
    {
      ret = libusb_control_transfer(handle,UM_REQUEST_TYPE,UM_REQUEST,USBBTN_VALUE,mesg,USBBTN_MESG_LENGTH,UM_TIMEOUT);
      debug ("Write result: %i",ret);
    }
    pos+=USBBTN_MESG_LENGTH;
  }

exit:
  if (transfer)
  {
    closeUSB(ctx,handle,USBBTN_INTERFACE);
  }
  else
  {
    log_info ("board array was not written out!!!");
  }
  return result;

error:
  return result;
}

我现在尝试以与写入功能相同的方式读取 USB 设备,但使用不同的 libusb_control_transfer 的参数,

> Setup Data (write)
>     bmRequestType: 0x21
>         0... .... = Direction: Host-to-device
>         .01. .... = Type: Class (0x1)
>         ...0 0001 = Recipient: Interface (0x01)
>         0010 0001 -> 0x21(hex)

我用这个参数来读取:

> Setup Data (read)
>     bmRequestType: 
>         1... .... = Direction: Device to Host
>         .01. .... = Type: Class (0x1)
>         ...0 0000 = Recipient: Device (0x00)
>               1010 0000  -> 0xa0(hex)

不工作的代码

bool readUSBButton(unsigned char* barray,unsigned int size)
{


 // barray[0] = 0x02;
 // barray[1] = 0x00;
 // barray[2] = 0x00;
 // barray[3] = 0x00;

 // result = writeUSBButton(barray,1,true,USBBTN_MESG_LENGTH);


  libusb_context *ctx = NULL;
  struct libusb_device_handle *handle = NULL;
  // USBBTN_MESG_LENGTH = 4 
  unsigned char mesg[USBBTN_MESG_LENGTH] = {0,autoconnect);

    if (!handle)
    {
      result = false;
      goto error;
    }
  }

  while (pos < size)
  {

    debug ("reading (%i): %x,mesg[3]);
    if (transfer)
    {   
     uint8_t buttonData;

      ret = libusb_control_transfer (handle,0xA0,2,&buttonData,0); 
      printf(" #### Read: %x  ######  ret= %i",buttonData,ret); 
      debug ("read result: %i",USBBTN_INTERFACE);
  }
  else
  {
    log_info ("board array was not read !!!");
  }
  return result;

error:
  return result;

}
  

lsusb -v 为我的设备输出

Bus 001 Device 006: ID d209:1200 Ultimarc
Device Descriptor:
  bLength                18
  bDescriptorType         1
  bcdUSB               2.00
  bDeviceClass            0
  bDeviceSubClass         0
  bDeviceProtocol         0
  bMaxPacketSize0         8
  idvendor           0xd209 Ultimarc
  idProduct          0x1200
  bcdDevice            0.01
  iManufacturer           2 USBButton
  iProduct                2 USBButton
  iSerial                 1 1
  bNumConfigurations      1
  Configuration Descriptor:
    bLength                 9
    bDescriptorType         2
    wTotalLength       0x003b
    bNumInterfaces          2
    bConfigurationValue     1
    iConfiguration          2 USBButton
    bmAttributes         0xa0
      (Bus Powered)
      Remote Wakeup
    MaxPower              100mA
    Interface Descriptor:
      bLength                 9
      bDescriptorType         4
      bInterfaceNumber        0
      bAlternateSetting       0
      bNumEndpoints           1
      bInterfaceClass         3 Human Interface Device
      bInterfaceSubClass      0
      bInterfaceProtocol      0
      iInterface              2 USBButton
        HID Device Descriptor:
          bLength                 9
          bDescriptorType        33
          bcdHID               1.11
          bCountryCode            0 Not supported
          bNumDescriptors         1
          bDescriptorType        34 Report
          wDescriptorLength      33
         Report Descriptors:
           ** UNAVAILABLE **
      Endpoint Descriptor:
        bLength                 7
        bDescriptorType         5
        bEndpointAddress     0x81  EP 1 IN
        bmAttributes            3
          Transfer Type            Interrupt
          Synch Type               None
          Usage Type               Data
        wMaxPacketSize     0x0008  1x 8 bytes
        bInterval              10
    Interface Descriptor:
      bLength                 9
      bDescriptorType         4
      bInterfaceNumber        1
      bAlternateSetting       0
      bNumEndpoints           1
      bInterfaceClass         3 Human Interface Device
      bInterfaceSubClass      1 Boot Interface Subclass
      bInterfaceProtocol      1 Keyboard
      iInterface              2 USBButton
        HID Device Descriptor:
          bLength                 9
          bDescriptorType        33
          bcdHID               1.11
          bCountryCode            0 Not supported
          bNumDescriptors         1
          bDescriptorType        34 Report
          wDescriptorLength     168
         Report Descriptors:
           ** UNAVAILABLE **
      Endpoint Descriptor:
        bLength                 7
        bDescriptorType         5
        bEndpointAddress     0x82  EP 2 IN
        bmAttributes            3
          Transfer Type            Interrupt
          Synch Type               None
          Usage Type               Data
        wMaxPacketSize     0x0008  1x 8 bytes
        bInterval              10
can't get device qualifier: Resource temporarily unavailable
can't get debug descriptor: Resource temporarily unavailable
Device Status:     0x0000
  (Bus Powered)

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。