diff --git a/tmk_core/protocol/usb_descriptor.c b/tmk_core/protocol/usb_descriptor.c index 6e710f659e..668ff8601c 100644 --- a/tmk_core/protocol/usb_descriptor.c +++ b/tmk_core/protocol/usb_descriptor.c @@ -454,7 +454,8 @@ const USB_Descriptor_Device_t PROGMEM DeviceDescriptor = { .Size = sizeof(USB_Descriptor_Device_t), .Type = DTYPE_Device }, - .USBSpecification = VERSION_BCD(2, 0, 0), + // Needs to be 2.0.1 or 2.1.0 to advertise BOS descriptor + .USBSpecification = VERSION_BCD(2, 1, 0), #if VIRTSER_ENABLE .Class = USB_CSCP_IADDeviceClass, @@ -481,6 +482,31 @@ const USB_Descriptor_Device_t PROGMEM DeviceDescriptor = { .NumberOfConfigurations = FIXED_NUM_CONFIGURATIONS }; +/* + * BOS descriptor + */ +const USB_Descriptor_Bos_t PROGMEM BosDescriptor = { + // 2 Bytes + .Header = { + .Size = 0x05, + .Type = DTYPE_Bos + }, + // 3 Bytes (=> 5 Bytes) + .TotalLength = 0x000C, + .NumDeviceCaps = 0x01, + + .Usb20ExtensionDevCap = { + // 2 Bytes (=> 7 Bytes) + .Header = { + .Size = 0x07, + .Type = 16, + }, + // 5 Bytes (=> 12 Bytes / 0x0C Bytes) + .DevCapabilityType = 2, + .Bytes = {0x00, 0x00, 0x00, 0x00}, + }, +}; + #ifndef USB_MAX_POWER_CONSUMPTION # define USB_MAX_POWER_CONSUMPTION 500 #endif @@ -1118,6 +1144,14 @@ uint16_t get_usb_descriptor(const uint16_t wValue, const uint16_t wIndex, const Address = &ConfigurationDescriptor; Size = sizeof(USB_Descriptor_Configuration_t); + break; + case DTYPE_Bos: + Address = &BosDescriptor; + Size = 5; + if (wLength >= sizeof(USB_Descriptor_Bos_t)) { + Size = sizeof(USB_Descriptor_Bos_t); + } + break; case DTYPE_String: switch (DescriptorIndex) { diff --git a/tmk_core/protocol/usb_descriptor.h b/tmk_core/protocol/usb_descriptor.h index ed84f4c9ab..68862f5fd7 100644 --- a/tmk_core/protocol/usb_descriptor.h +++ b/tmk_core/protocol/usb_descriptor.h @@ -309,3 +309,68 @@ enum usb_endpoints { #define DIGITIZER_EPSIZE 8 uint16_t get_usb_descriptor(const uint16_t wValue, const uint16_t wIndex, const uint16_t wLength, const void** const DescriptorAddress); + + +// Defining the types that LUFA doesn't +enum USB_DescriptorTypes_tmk_t +{ + DTYPE_Otg = 0x09, + DTYPE_Debug = 0x0A, + DTYPE_Bos = 0x0F, /**< Indicates that the descriptor is a binary object store descriptor. */ + DTYPE_DeviceCapability = 0x10, /**< Indicates that the descriptor is a device capability descriptor. */ +}; +typedef struct +{ + USB_Descriptor_Header_t Header; /**< Descriptor header, including type and size. */ + + uint8_t DevCapabilityType; /**< TODO + */ + uint8_t Bytes[]; /**< Capability-specific format + */ +} ATTR_PACKED USB_Descriptor_Capability_t; +typedef struct +{ + USB_Descriptor_Header_t Header; /**< Descriptor header, including type and size. */ + + uint8_t DevCapabilityType; /**< TODO + */ + uint8_t Bytes[4]; /**< Capability-specific format + */ +} ATTR_PACKED USB_Descriptor_Capability_Usb20Ext_t; + +/** \brief Standard USB BOS Descriptor (LUFA naming conventions). + * + * Type define for a standard BOS Descriptor. This structure uses LUFA-specific element names + * to make each element's purpose clearer. + * + * \note Regardless of CPU architecture, these values should be stored as little endian. + */ +typedef struct +{ + USB_Descriptor_Header_t Header; /**< Descriptor header, including type and size. */ + + uint16_t TotalLength; /**< Length of this descriptor and all its sub descriptors. + */ + uint8_t NumDeviceCaps; /**< The number of separate device capability descriptors in the BOS. + */ + USB_Descriptor_Capability_Usb20Ext_t Usb20ExtensionDevCap; +} ATTR_PACKED USB_Descriptor_Bos_t; + +/** \brief Standard USB BOS Descriptor (USB-IF naming conventions). + * + * Type define for a standard BOS Descriptor. This structure uses the relevant standard's given + * element names to ensure compatibility with the standard. + * + * \note Regardless of CPU architecture, these values should be stored as little endian. + */ +typedef struct +{ + uint8_t bLength; /**< Size of the descriptor, in bytes. */ + uint8_t bDescriptorType; /**< Type of the descriptor, either a value in \ref USB_DescriptorTypes_t or a + * value given by the specific class. + */ + uint16_t wTotalLength; /**< Length of this descriptor and all its sub descriptors. + */ + uint8_t bNumDeviceCaps; /**< The number of separate device capability descriptors in the BOS. + */ +} ATTR_PACKED USB_StdDescriptor_Bos_t;