qemu/hw/usb/desc.h
<<
>>
Prefs
   1#ifndef QEMU_HW_USB_DESC_H
   2#define QEMU_HW_USB_DESC_H
   3
   4#include <wchar.h>
   5
   6/* binary representation */
   7typedef struct USBDescriptor {
   8    uint8_t                   bLength;
   9    uint8_t                   bDescriptorType;
  10    union {
  11        struct {
  12            uint8_t           bcdUSB_lo;
  13            uint8_t           bcdUSB_hi;
  14            uint8_t           bDeviceClass;
  15            uint8_t           bDeviceSubClass;
  16            uint8_t           bDeviceProtocol;
  17            uint8_t           bMaxPacketSize0;
  18            uint8_t           idVendor_lo;
  19            uint8_t           idVendor_hi;
  20            uint8_t           idProduct_lo;
  21            uint8_t           idProduct_hi;
  22            uint8_t           bcdDevice_lo;
  23            uint8_t           bcdDevice_hi;
  24            uint8_t           iManufacturer;
  25            uint8_t           iProduct;
  26            uint8_t           iSerialNumber;
  27            uint8_t           bNumConfigurations;
  28        } device;
  29        struct {
  30            uint8_t           bcdUSB_lo;
  31            uint8_t           bcdUSB_hi;
  32            uint8_t           bDeviceClass;
  33            uint8_t           bDeviceSubClass;
  34            uint8_t           bDeviceProtocol;
  35            uint8_t           bMaxPacketSize0;
  36            uint8_t           bNumConfigurations;
  37            uint8_t           bReserved;
  38        } device_qualifier;
  39        struct {
  40            uint8_t           wTotalLength_lo;
  41            uint8_t           wTotalLength_hi;
  42            uint8_t           bNumInterfaces;
  43            uint8_t           bConfigurationValue;
  44            uint8_t           iConfiguration;
  45            uint8_t           bmAttributes;
  46            uint8_t           bMaxPower;
  47        } config;
  48        struct {
  49            uint8_t           bInterfaceNumber;
  50            uint8_t           bAlternateSetting;
  51            uint8_t           bNumEndpoints;
  52            uint8_t           bInterfaceClass;
  53            uint8_t           bInterfaceSubClass;
  54            uint8_t           bInterfaceProtocol;
  55            uint8_t           iInterface;
  56        } interface;
  57        struct {
  58            uint8_t           bEndpointAddress;
  59            uint8_t           bmAttributes;
  60            uint8_t           wMaxPacketSize_lo;
  61            uint8_t           wMaxPacketSize_hi;
  62            uint8_t           bInterval;
  63            uint8_t           bRefresh;        /* only audio ep */
  64            uint8_t           bSynchAddress;   /* only audio ep */
  65        } endpoint;
  66        struct {
  67            uint8_t           bMaxBurst;
  68            uint8_t           bmAttributes;
  69            uint8_t           wBytesPerInterval_lo;
  70            uint8_t           wBytesPerInterval_hi;
  71        } super_endpoint;
  72        struct {
  73            uint8_t           wTotalLength_lo;
  74            uint8_t           wTotalLength_hi;
  75            uint8_t           bNumDeviceCaps;
  76        } bos;
  77        struct {
  78            uint8_t           bDevCapabilityType;
  79            union {
  80                struct {
  81                    uint8_t   bmAttributes_1;
  82                    uint8_t   bmAttributes_2;
  83                    uint8_t   bmAttributes_3;
  84                    uint8_t   bmAttributes_4;
  85                } usb2_ext;
  86                struct {
  87                    uint8_t   bmAttributes;
  88                    uint8_t   wSpeedsSupported_lo;
  89                    uint8_t   wSpeedsSupported_hi;
  90                    uint8_t   bFunctionalitySupport;
  91                    uint8_t   bU1DevExitLat;
  92                    uint8_t   wU2DevExitLat_lo;
  93                    uint8_t   wU2DevExitLat_hi;
  94                } super;
  95            } u;
  96        } cap;
  97    } u;
  98} QEMU_PACKED USBDescriptor;
  99
 100struct USBDescID {
 101    uint16_t                  idVendor;
 102    uint16_t                  idProduct;
 103    uint16_t                  bcdDevice;
 104    uint8_t                   iManufacturer;
 105    uint8_t                   iProduct;
 106    uint8_t                   iSerialNumber;
 107};
 108
 109struct USBDescDevice {
 110    uint16_t                  bcdUSB;
 111    uint8_t                   bDeviceClass;
 112    uint8_t                   bDeviceSubClass;
 113    uint8_t                   bDeviceProtocol;
 114    uint8_t                   bMaxPacketSize0;
 115    uint8_t                   bNumConfigurations;
 116
 117    const USBDescConfig       *confs;
 118};
 119
 120struct USBDescConfig {
 121    uint8_t                   bNumInterfaces;
 122    uint8_t                   bConfigurationValue;
 123    uint8_t                   iConfiguration;
 124    uint8_t                   bmAttributes;
 125    uint8_t                   bMaxPower;
 126
 127    /* grouped interfaces */
 128    uint8_t                   nif_groups;
 129    const USBDescIfaceAssoc   *if_groups;
 130
 131    /* "normal" interfaces */
 132    uint8_t                   nif;
 133    const USBDescIface        *ifs;
 134};
 135
 136/* conceptually an Interface Association Descriptor, and releated interfaces */
 137struct USBDescIfaceAssoc {
 138    uint8_t                   bFirstInterface;
 139    uint8_t                   bInterfaceCount;
 140    uint8_t                   bFunctionClass;
 141    uint8_t                   bFunctionSubClass;
 142    uint8_t                   bFunctionProtocol;
 143    uint8_t                   iFunction;
 144
 145    uint8_t                   nif;
 146    const USBDescIface        *ifs;
 147};
 148
 149struct USBDescIface {
 150    uint8_t                   bInterfaceNumber;
 151    uint8_t                   bAlternateSetting;
 152    uint8_t                   bNumEndpoints;
 153    uint8_t                   bInterfaceClass;
 154    uint8_t                   bInterfaceSubClass;
 155    uint8_t                   bInterfaceProtocol;
 156    uint8_t                   iInterface;
 157
 158    uint8_t                   ndesc;
 159    USBDescOther              *descs;
 160    USBDescEndpoint           *eps;
 161};
 162
 163struct USBDescEndpoint {
 164    uint8_t                   bEndpointAddress;
 165    uint8_t                   bmAttributes;
 166    uint16_t                  wMaxPacketSize;
 167    uint8_t                   bInterval;
 168    uint8_t                   bRefresh;
 169    uint8_t                   bSynchAddress;
 170
 171    uint8_t                   is_audio; /* has bRefresh + bSynchAddress */
 172    uint8_t                   *extra;
 173
 174    /* superspeed endpoint companion */
 175    uint8_t                   bMaxBurst;
 176    uint8_t                   bmAttributes_super;
 177    uint16_t                  wBytesPerInterval;
 178};
 179
 180struct USBDescOther {
 181    uint8_t                   length;
 182    const uint8_t             *data;
 183};
 184
 185struct USBDescMSOS {
 186    const char                *CompatibleID;
 187    const wchar_t             *Label;
 188    bool                      SelectiveSuspendEnabled;
 189};
 190
 191typedef const char *USBDescStrings[256];
 192
 193struct USBDesc {
 194    USBDescID                 id;
 195    const USBDescDevice       *full;
 196    const USBDescDevice       *high;
 197    const USBDescDevice       *super;
 198    const char* const         *str;
 199    const USBDescMSOS         *msos;
 200};
 201
 202#define USB_DESC_FLAG_SUPER (1 << 1)
 203
 204/* little helpers */
 205static inline uint8_t usb_lo(uint16_t val)
 206{
 207    return val & 0xff;
 208}
 209
 210static inline uint8_t usb_hi(uint16_t val)
 211{
 212    return (val >> 8) & 0xff;
 213}
 214
 215/* generate usb packages from structs */
 216int usb_desc_device(const USBDescID *id, const USBDescDevice *dev,
 217                    bool msos, uint8_t *dest, size_t len);
 218int usb_desc_device_qualifier(const USBDescDevice *dev,
 219                              uint8_t *dest, size_t len);
 220int usb_desc_config(const USBDescConfig *conf, int flags,
 221                    uint8_t *dest, size_t len);
 222int usb_desc_iface_group(const USBDescIfaceAssoc *iad, int flags,
 223                         uint8_t *dest, size_t len);
 224int usb_desc_iface(const USBDescIface *iface, int flags,
 225                   uint8_t *dest, size_t len);
 226int usb_desc_endpoint(const USBDescEndpoint *ep, int flags,
 227                      uint8_t *dest, size_t len);
 228int usb_desc_other(const USBDescOther *desc, uint8_t *dest, size_t len);
 229int usb_desc_msos(const USBDesc *desc, USBPacket *p,
 230                  int index, uint8_t *dest, size_t len);
 231
 232/* control message emulation helpers */
 233void usb_desc_init(USBDevice *dev);
 234void usb_desc_attach(USBDevice *dev);
 235void usb_desc_set_string(USBDevice *dev, uint8_t index, const char *str);
 236void usb_desc_create_serial(USBDevice *dev);
 237const char *usb_desc_get_string(USBDevice *dev, uint8_t index);
 238int usb_desc_string(USBDevice *dev, int index, uint8_t *dest, size_t len);
 239int usb_desc_get_descriptor(USBDevice *dev, USBPacket *p,
 240        int value, uint8_t *dest, size_t len);
 241int usb_desc_handle_control(USBDevice *dev, USBPacket *p,
 242        int request, int value, int index, int length, uint8_t *data);
 243
 244#endif /* QEMU_HW_USB_DESC_H */
 245