Author Topic: Emulate three USB devices with one Teensy device  (Read 2344 times)

0 Members and 1 Guest are viewing this topic.

Offline luiHSTopic starter

  • Frequent Contributor
  • **
  • Posts: 612
  • Country: es
Emulate three USB devices with one Teensy device
« on: March 07, 2019, 07:12:49 am »
 
Hello.

I need emulate three USB devices (Mouse, Keyboard, Xbox360 gamepad), with one Teensy board (based on kinetis MK20, MK22, MKL26, MK64 or MK66 microcontroller).

I have modify the USB descriptors to add support to Xbox360, the code compile but only can emulate Mouse/Keyboard or Xbox360, not the three. Mouse and Keyboard are HID, Xbox360 is Xinput device.

If I put these VID PID then work emulating an Xbox360 gamepad
  #define VENDOR_ID   0x045e
  #define PRODUCT_ID   0x028e

If I put these VID PID then work and emulate a Mouse + Keyboard
  #define VENDOR_ID   0x16C0
  #define PRODUCT_ID   0x0482

I do not know what is the problem, and if its really possible mix HID and non HID USB devices to emulate with one microcontroller.

Regards

« Last Edit: March 07, 2019, 07:18:09 am by luiHS »
 

Offline up8051

  • Frequent Contributor
  • **
  • Posts: 335
  • Country: pl
Re: Emulate three USB devices with one Teensy device
« Reply #1 on: March 07, 2019, 09:30:10 am »
Did you try to build composite device?
Show the descriptors for HID and XInput.

Regards
up8051
 

Offline Xmaxyama

  • Newbie
  • Posts: 2
  • Country: ad
Re: Emulate three USB devices with one Teensy device
« Reply #2 on: March 07, 2019, 09:41:29 am »
Each of these stories may not be the same.

Offline luiHSTopic starter

  • Frequent Contributor
  • **
  • Posts: 612
  • Country: es
Re: Emulate three USB devices with one Teensy device
« Reply #3 on: March 07, 2019, 04:31:18 pm »
Did you try to build composite device?
Show the descriptors for HID and XInput.

Regards
up8051

Yes, a USB composite device.
First there is a source file with several defines, according the USB device that I choose from and Arduino Menu. Here I define the interfaces, endpoints, VID, PID and some values for the descriptors.

This is what I have configure for my composite USB device, where I have try with two sets of VID/PID, I can only define one set, I tried with these two pair of VID/PID, one only work for Xbox360 gamepad, the other only for Keyboard/Mouse:

Code: [Select]
  // This work only with Xinput
  #define VENDOR_ID 0x045e
  #define PRODUCT_ID 0x028e

  // And this work only with Mouse - Keyboard (HID devices)
  //#define VENDOR_ID 0x16C0
  //#define PRODUCT_ID 0x0482
   
  #define MANUFACTURER_NAME {'©','M','i','c','r','o','s','o','f','t'}
  #define MANUFACTURER_NAME_LEN 10
  #define PRODUCT_NAME {'C','o','n','t','r','o','l','l','e','r'}
  #define PRODUCT_NAME_LEN 10
  #define EP0_SIZE 64
  #define NUM_ENDPOINTS     11
  #define NUM_USB_BUFFERS 31
  #define NUM_INTERFACE 8
 
  #define SEREMU_INTERFACE      4 // Serial emulation
  #define SEREMU_TX_ENDPOINT    7
  #define SEREMU_TX_SIZE        64
  #define SEREMU_TX_INTERVAL    1
  #define SEREMU_RX_ENDPOINT    8
  #define SEREMU_RX_SIZE        32
  #define SEREMU_RX_INTERVAL    2
 
  #define KEYBOARD_INTERFACE    5 // Keyboard
  #define KEYBOARD_ENDPOINT     9
  #define KEYBOARD_SIZE         8
  #define KEYBOARD_INTERVAL     1
 
  #define KEYMEDIA_INTERFACE    6 // Keyboard Media Keys
  #define KEYMEDIA_ENDPOINT    10
  #define KEYMEDIA_SIZE         8
  #define KEYMEDIA_INTERVAL     4
 
  #define MOUSE_INTERFACE       7 // Mouse
  #define MOUSE_ENDPOINT       11
  #define MOUSE_SIZE            8
  #define MOUSE_INTERVAL        1
 
  #define XINPUT_INTERFACE 0  // XINPUT 4 interfaces (0, 1, 2, 3) with 6 Endpoints
  #define XINPUT_RX_ENDPOINT 2
  #define XINPUT_RX_SIZE         8
  #define XINPUT_TX_ENDPOINT 1
  #define XINPUT_TX_SIZE        20
 
  #define ENDPOINT1_CONFIG ENDPOINT_TRANSIMIT_ONLY
  #define ENDPOINT2_CONFIG ENDPOINT_RECEIVE_ONLY
  #define ENDPOINT3_CONFIG ENDPOINT_TRANSIMIT_ONLY
  #define ENDPOINT4_CONFIG ENDPOINT_RECEIVE_ONLY
  #define ENDPOINT5_CONFIG ENDPOINT_TRANSMIT_AND_RECEIVE
  #define ENDPOINT6_CONFIG ENDPOINT_TRANSIMIT_ONLY
 
  #define ENDPOINT7_CONFIG ENDPOINT_TRANSIMIT_ONLY
  #define ENDPOINT8_CONFIG ENDPOINT_RECEIVE_ONLY
  #define ENDPOINT9_CONFIG ENDPOINT_TRANSIMIT_ONLY
  #define ENDPOINT10_CONFIG ENDPOINT_TRANSIMIT_ONLY
  #define ENDPOINT11_CONFIG ENDPOINT_TRANSIMIT_ONLY 



And these are the USB descriptors for each interface.

Code: [Select]
#ifdef SEREMU_INTERFACE
        // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12
        9,                                      // bLength
        4,                                      // bDescriptorType
        SEREMU_INTERFACE,                       // bInterfaceNumber
        0,                                      // bAlternateSetting
        2,                                      // bNumEndpoints
        0x03,                                   // bInterfaceClass (0x03 = HID)
        0x00,                                   // bInterfaceSubClass
        0x00,                                   // bInterfaceProtocol
        0,                                      // iInterface
        // HID interface descriptor, HID 1.11 spec, section 6.2.1
        9,                                      // bLength
        0x21,                                   // bDescriptorType
        0x11, 0x01,                             // bcdHID
        0,                                      // bCountryCode
        1,                                      // bNumDescriptors
        0x22,                                   // bDescriptorType
        LSB(sizeof(seremu_report_desc)),        // wDescriptorLength
        MSB(sizeof(seremu_report_desc)),
        // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
        7,                                      // bLength
        5,                                      // bDescriptorType
        SEREMU_TX_ENDPOINT | 0x80,              // bEndpointAddress
        0x03,                                   // bmAttributes (0x03=intr)
        SEREMU_TX_SIZE, 0,                      // wMaxPacketSize
        SEREMU_TX_INTERVAL,                     // bInterval
        // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
        7,                                      // bLength
        5,                                      // bDescriptorType
        SEREMU_RX_ENDPOINT,                     // bEndpointAddress
        0x03,                                   // bmAttributes (0x03=intr)
        SEREMU_RX_SIZE, 0,                      // wMaxPacketSize
        SEREMU_RX_INTERVAL, // bInterval
#endif // SEREMU_INTERFACE


Code: [Select]
#ifdef KEYBOARD_INTERFACE
        // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12
        9,                                      // bLength
        4,                                      // bDescriptorType
        KEYBOARD_INTERFACE,                     // bInterfaceNumber
        0,                                      // bAlternateSetting
        1,                                      // bNumEndpoints
        0x03,                                   // bInterfaceClass (0x03 = HID)
        0x01,                                   // bInterfaceSubClass (0x01 = Boot)
        0x01,                                   // bInterfaceProtocol (0x01 = Keyboard)
        0,                                      // iInterface
        // HID interface descriptor, HID 1.11 spec, section 6.2.1
        9,                                      // bLength
        0x21,                                   // bDescriptorType
        0x11, 0x01,                             // bcdHID
        0,                                      // bCountryCode
        1,                                      // bNumDescriptors
        0x22,                                   // bDescriptorType
        LSB(sizeof(keyboard_report_desc)),      // wDescriptorLength
        MSB(sizeof(keyboard_report_desc)),
        // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
        7,                                      // bLength
        5,                                      // bDescriptorType
        KEYBOARD_ENDPOINT | 0x80,               // bEndpointAddress
        0x03,                                   // bmAttributes (0x03=intr)
        KEYBOARD_SIZE, 0,                       // wMaxPacketSize
        KEYBOARD_INTERVAL,                      // bInterval
#endif // KEYBOARD_INTERFACE


Code: [Select]
#ifdef KEYMEDIA_INTERFACE
        // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12
        9,                                      // bLength
        4,                                      // bDescriptorType
        KEYMEDIA_INTERFACE,                     // bInterfaceNumber
        0,                                      // bAlternateSetting
        1,                                      // bNumEndpoints
        0x03,                                   // bInterfaceClass (0x03 = HID)
        0x00,                                   // bInterfaceSubClass
        0x00,                                   // bInterfaceProtocol
        0,                                      // iInterface
        // HID interface descriptor, HID 1.11 spec, section 6.2.1
        9,                                      // bLength
        0x21,                                   // bDescriptorType
        0x11, 0x01,                             // bcdHID
        0,                                      // bCountryCode
        1,                                      // bNumDescriptors
        0x22,                                   // bDescriptorType
        LSB(sizeof(keymedia_report_desc)),      // wDescriptorLength
        MSB(sizeof(keymedia_report_desc)),
        // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
        7,                                      // bLength
        5,                                      // bDescriptorType
        KEYMEDIA_ENDPOINT | 0x80,               // bEndpointAddress
        0x03,                                   // bmAttributes (0x03=intr)
        KEYMEDIA_SIZE, 0,                       // wMaxPacketSize
        KEYMEDIA_INTERVAL,                      // bInterval
#endif // KEYMEDIA_INTERFACE


Code: [Select]
#ifdef MOUSE_INTERFACE
        // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12
        9,                                      // bLength
        4,                                      // bDescriptorType
        MOUSE_INTERFACE,                        // bInterfaceNumber
        0,                                      // bAlternateSetting
        1,                                      // bNumEndpoints
        0x03,                                   // bInterfaceClass (0x03 = HID)
        0x00,                                   // bInterfaceSubClass (0x01 = Boot)
        0x00,                                   // bInterfaceProtocol (0x02 = Mouse)
        0,                                      // iInterface
        // HID interface descriptor, HID 1.11 spec, section 6.2.1
        9,                                      // bLength
        0x21,                                   // bDescriptorType
        0x11, 0x01,                             // bcdHID
        0,                                      // bCountryCode
        1,                                      // bNumDescriptors
        0x22,                                   // bDescriptorType
        LSB(sizeof(mouse_report_desc)),         // wDescriptorLength
        MSB(sizeof(mouse_report_desc)),
        // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
        7,                                      // bLength
        5,                                      // bDescriptorType
        MOUSE_ENDPOINT | 0x80,                  // bEndpointAddress
        0x03,                                   // bmAttributes (0x03=intr)
        MOUSE_SIZE, 0,                          // wMaxPacketSize
        MOUSE_INTERVAL,                         // bInterval
#endif // MOUSE_INTERFACE


Code: [Select]
#ifdef XINPUT_INTERFACE
//Interface 0
9, //bLength (length of interface descriptor 9 bytes)
4, //bDescriptorType (4 is interface)
0, //bInterfaceNumber (This is interface 0)
0, //bAlternateSetting (used to select alternate setting.  notused)
2, //bNumEndpoints (this interface has 2 endpoints)
0xFF, //bInterfaceClass (Vendor Defined is 255)
0x5D, //bInterfaceSubClass
0x01, //bInterfaceProtocol
0, //iInterface (Index of string descriptor for describing this notused)
//Some sort of common descriptor? I pulled this from Message Analyzer dumps of an actual controller
17,33,0,1,1,37,129,20,0,0,0,0,19,2,8,0,0,
//Endpoint 1 IN
7, //bLength (length of ep1in in descriptor 7 bytes)
5, //bDescriptorType (5 is endpoint)
0x81, //bEndpointAddress (0x81 is IN1)
0x03, //bmAttributes (0x03 is interrupt no synch, usage type data)
0x20, 0x00, //wMaxPacketSize (0x0020 is 1x32 bytes)
4, //bInterval (polling interval in frames 4 frames)
//Endpoint 2 OUT
7, //bLength (length of ep2out in descriptor 7 bytes)
5, //bDescriptorType (5 is endpoint)
0x02, //bEndpointAddress (0x02 is OUT2)
0x03, //bmAttributes (0x03 is interrupt no synch, usage type data)
0x20, 0x00, //wMaxPacketSize (0x0020 is 1x32 bytes)
8, //bInterval (polling interval in frames 8 frames)
//Interface 1
9, //bLength (length of interface descriptor 9 bytes)
4, //bDescriptorType (4 is interface)
1, //bInterfaceNumber (This is interface 1)
0, //bAlternateSetting (used to select alternate setting.  notused)
4, //bNumEndpoints (this interface has 4 endpoints)
0xFF, //bInterfaceClass (Vendor Defined is 255)
0x5D, //bInterfaceSubClass (93)
0x03, //bInterfaceProtocol (3)
0, //iInterface (Index of string descriptor for describing this notused)
//A different common descriptor? I pulled this from Message Analyzer dumps of an actual controller
27,33,0,1,1,1,131,64,1,4,32,22,133,0,0,0,0,0,0,22,5,0,0,0,0,0,0,
//Endpoint 3 IN
7, //bLength (length of ep3in descriptor 7 bytes)
5, //bDescriptorType (5 is endpoint)
0x83, //bEndpointAddress (0x83 is IN3)
0x03, //bmAttributes (0x03 is interrupt no synch, usage type data)
0x20, 0x00, //wMaxPacketSize (0x0020 is 1x32 bytes)
2, //bInterval (polling interval in frames 2 frames)
//Endpoint 4 OUT
7, //bLength (length of ep4out descriptor 7 bytes)
5, //bDescriptorType (5 is endpoint)
0x04, //bEndpointAddress (0x04 is OUT4)
0x03, //bmAttributes (0x03 is interrupt no synch, usage type data)
0x20, 0x00, //wMaxPacketSize (0x0020 is 1x32 bytes)
4, //bInterval (polling interval in frames 4 frames)
//Endpoint 5 IN
7, //bLength (length of ep5in descriptor 7 bytes)
5, //bDescriptorType (5 is endpoint)
0x85, //bEndpointAddress (0x85 is IN5)
0x03, //bmAttributes (0x03 is interrupt no synch, usage type data)
0x20, 0x00, //wMaxPacketSize (0x0020 is 1x32 bytes)
64, //bInterval (polling interval in frames 64 frames)
//Endpoint 5 OUT (shares endpoint number with previous)
7, //bLength (length of ep5out descriptor 7 bytes)
5, //bDescriptorType (5 is endpoint)
0x05, //bEndpointAddress (0x05 is OUT5)
0x03, //bmAttributes (0x03 is interrupt no synch, usage type data)
0x20, 0x00, //wMaxPacketSize (0x0020 is 1x32 bytes)
16, //bInterval (polling interval in frames 16 frames)
//Interface 2
9, //bLength (length of interface descriptor 9 bytes)
4, //bDescriptorType (4 is interface)
2, //bInterfaceNumber (This is interface 2)
0, //bAlternateSetting (used to select alternate setting.  notused)
1, //bNumEndpoints (this interface has 4 endpoints)
0xFF, //bInterfaceClass (Vendor Defined is 255)
0x5D, //bInterfaceSubClass (93)
0x02, //bInterfaceProtocol (3)
0, //iInterface (Index of string descriptor for describing this notused)
//Common Descriptor.  Seems that these come after every interface description?
9,33,0,1,1,34,134,7,0,
//Endpoint 6 IN
7, //bLength (length of ep6in descriptor 7 bytes)
5, //bDescriptorType (5 is endpoint)
0x86, //bEndpointAddress (0x86 is IN6)
0x03, //bmAttributes (0x03 is interrupt no synch, usage type data)
0x20, 0x00, //wMaxPacketSize (0x0020 is 1x32 bytes)
16, //bInterval (polling interval in frames 64 frames)+
//Interface 3
//This is the interface on which all the security handshaking takes place
//We don't use this but it could be used for man-in-the-middle stuff
9, //bLength (length of interface descriptor 9 bytes)
4, //bDescriptorType (4 is interface)
3, //bInterfaceNumber (This is interface 3)
0, //bAlternateSetting (used to select alternate setting.  notused)
0, //bNumEndpoints (this interface has 0 endpoints ??? )
0xFF, //bInterfaceClass (Vendor Defined is 255)
0xFD, //bInterfaceSubClass (253)
0x13, //bInterfaceProtocol (19)
4, //iInterface (Computer never asks for this, but an x360 would. so include one day?)
//Another interface another Common Descriptor
6,65,0,1,1,3

#endif // XINPUT_INTERFACE
« Last Edit: March 07, 2019, 04:53:03 pm by luiHS »
 


Share me

Digg  Facebook  SlashDot  Delicious  Technorati  Twitter  Google  Yahoo
Smf