2019-04-16 05:56:01 +03:00
===============
USB/IP protocol
===============
2021-03-30 20:00:13 +03:00
Architecture
============
2011-08-22 05:52:47 +04:00
The USB/IP protocol follows a server/client architecture. The server exports the
2021-03-30 20:00:13 +03:00
USB devices and the clients import them. The device driver for the exported
2011-08-22 05:52:47 +04:00
USB device runs on the client machine.
The client may ask for the list of the exported USB devices. To get the list the
2021-03-30 20:00:13 +03:00
client opens a TCP/IP connection to the server, and sends an OP_REQ_DEVLIST
2011-08-22 05:52:47 +04:00
packet on top of the TCP/IP connection (so the actual OP_REQ_DEVLIST may be sent
in one or more pieces at the low level transport layer). The server sends back
the OP_REP_DEVLIST packet which lists the exported USB devices. Finally the
TCP/IP connection is closed.
2019-04-16 05:56:01 +03:00
::
2011-08-22 05:52:47 +04:00
virtual host controller usb host
"client" "server"
(imports USB devices) (exports USB devices)
| |
| OP_REQ_DEVLIST |
| ----------------------------------------------> |
| |
| OP_REP_DEVLIST |
| <---------------------------------------------- |
| |
Once the client knows the list of exported USB devices it may decide to use one
2021-03-30 20:00:13 +03:00
of them. First the client opens a TCP/IP connection to the server and
2011-08-22 05:52:47 +04:00
sends an OP_REQ_IMPORT packet. The server replies with OP_REP_IMPORT. If the
import was successful the TCP/IP connection remains open and will be used
2012-04-06 18:33:52 +04:00
to transfer the URB traffic between the client and the server. The client may
2011-08-22 05:52:47 +04:00
send two types of packets: the USBIP_CMD_SUBMIT to submit an URB, and
USBIP_CMD_UNLINK to unlink a previously submitted URB. The answers of the
server may be USBIP_RET_SUBMIT and USBIP_RET_UNLINK respectively.
2019-04-16 05:56:01 +03:00
::
2011-08-22 05:52:47 +04:00
virtual host controller usb host
"client" "server"
(imports USB devices) (exports USB devices)
| |
| OP_REQ_IMPORT |
| ----------------------------------------------> |
| |
| OP_REP_IMPORT |
| <---------------------------------------------- |
| |
| |
| USBIP_CMD_SUBMIT(seqnum = n) |
| ----------------------------------------------> |
| |
| USBIP_RET_SUBMIT(seqnum = n) |
| <---------------------------------------------- |
| . |
| : |
| |
| USBIP_CMD_SUBMIT(seqnum = m) |
| ----------------------------------------------> |
| |
| USBIP_CMD_SUBMIT(seqnum = m+1) |
| ----------------------------------------------> |
| |
| USBIP_CMD_SUBMIT(seqnum = m+2) |
| ----------------------------------------------> |
| |
| USBIP_RET_SUBMIT(seqnum = m) |
| <---------------------------------------------- |
| |
| USBIP_CMD_SUBMIT(seqnum = m+3) |
| ----------------------------------------------> |
| |
| USBIP_RET_SUBMIT(seqnum = m+1) |
| <---------------------------------------------- |
| |
| USBIP_CMD_SUBMIT(seqnum = m+4) |
| ----------------------------------------------> |
| |
| USBIP_RET_SUBMIT(seqnum = m+2) |
| <---------------------------------------------- |
| . |
| : |
2021-03-30 20:00:13 +03:00
For UNLINK, note that after a successful USBIP_RET_UNLINK, the unlinked URB
submission would not have a corresponding USBIP_RET_SUBMIT (this is explained in
function stub_recv_cmd_unlink of drivers/usb/usbip/stub_rx.c).
::
virtual host controller usb host
"client" "server"
(imports USB devices) (exports USB devices)
| |
| USBIP_CMD_SUBMIT(seqnum = p) |
| ----------------------------------------------> |
2011-08-22 05:52:47 +04:00
| |
| USBIP_CMD_UNLINK |
2021-03-30 20:00:13 +03:00
| (seqnum = p+1, unlink_seqnum = p) |
2011-08-22 05:52:47 +04:00
| ----------------------------------------------> |
| |
| USBIP_RET_UNLINK |
2021-03-30 20:00:13 +03:00
| (seqnum = p+1, status = -ECONNRESET) |
| <---------------------------------------------- |
| |
| Note: No USBIP_RET_SUBMIT(seqnum = p) |
| <--X---X---X---X---X---X---X---X---X---X---X--- |
| . |
| : |
| |
| USBIP_CMD_SUBMIT(seqnum = q) |
| ----------------------------------------------> |
| |
| USBIP_RET_SUBMIT(seqnum = q) |
| <---------------------------------------------- |
| |
| USBIP_CMD_UNLINK |
| (seqnum = q+1, unlink_seqnum = q) |
| ----------------------------------------------> |
| |
| USBIP_RET_UNLINK |
| (seqnum = q+1, status = 0) |
2011-08-22 05:52:47 +04:00
| <---------------------------------------------- |
| |
The fields are in network (big endian) byte order meaning that the most significant
byte (MSB) is stored at the lowest address.
2021-03-30 20:00:13 +03:00
Protocol Version
================
The documented USBIP version is v1.1.1. The binary representation of this
version in message headers is 0x0111.
This is defined in tools/usb/usbip/configure.ac
Message Format
==============
2011-08-22 05:52:47 +04:00
2019-04-16 05:56:01 +03:00
OP_REQ_DEVLIST:
Retrieve the list of exported USB devices.
2011-08-22 05:52:47 +04:00
2019-04-16 05:56:01 +03:00
+-----------+--------+------------+---------------------------------------------------+
| Offset | Length | Value | Description |
+===========+========+============+===================================================+
2021-03-30 20:00:13 +03:00
| 0 | 2 | | USBIP version |
2019-04-16 05:56:01 +03:00
+-----------+--------+------------+---------------------------------------------------+
| 2 | 2 | 0x8005 | Command code: Retrieve the list of exported USB |
| | | | devices. |
+-----------+--------+------------+---------------------------------------------------+
| 4 | 4 | 0x00000000 | Status: unused, shall be set to 0 |
+-----------+--------+------------+---------------------------------------------------+
2011-08-22 05:52:47 +04:00
2019-04-16 05:56:01 +03:00
OP_REP_DEVLIST:
Reply with the list of exported USB devices.
2011-08-22 05:52:47 +04:00
2019-04-16 05:56:01 +03:00
+-----------+--------+------------+---------------------------------------------------+
| Offset | Length | Value | Description |
+===========+========+============+===================================================+
2021-03-30 20:00:13 +03:00
| 0 | 2 | | USBIP version |
2019-04-16 05:56:01 +03:00
+-----------+--------+------------+---------------------------------------------------+
| 2 | 2 | 0x0005 | Reply code: The list of exported USB devices. |
+-----------+--------+------------+---------------------------------------------------+
| 4 | 4 | 0x00000000 | Status: 0 for OK |
+-----------+--------+------------+---------------------------------------------------+
| 8 | 4 | n | Number of exported devices: 0 means no exported |
| | | | devices. |
+-----------+--------+------------+---------------------------------------------------+
| 0x0C | | | From now on the exported n devices are described, |
| | | | if any. If no devices are exported the message |
| | | | ends with the previous "number of exported |
| | | | devices" field. |
+-----------+--------+------------+---------------------------------------------------+
| | 256 | | path: Path of the device on the host exporting the|
| | | | USB device, string closed with zero byte, e.g. |
| | | | "/sys/devices/pci0000:00/0000:00:1d.1/usb3/3-2" |
| | | | The unused bytes shall be filled with zero |
| | | | bytes. |
+-----------+--------+------------+---------------------------------------------------+
| 0x10C | 32 | | busid: Bus ID of the exported device, string |
| | | | closed with zero byte, e.g. "3-2". The unused |
| | | | bytes shall be filled with zero bytes. |
+-----------+--------+------------+---------------------------------------------------+
| 0x12C | 4 | | busnum |
+-----------+--------+------------+---------------------------------------------------+
| 0x130 | 4 | | devnum |
+-----------+--------+------------+---------------------------------------------------+
| 0x134 | 4 | | speed |
+-----------+--------+------------+---------------------------------------------------+
| 0x138 | 2 | | idVendor |
+-----------+--------+------------+---------------------------------------------------+
| 0x13A | 2 | | idProduct |
+-----------+--------+------------+---------------------------------------------------+
| 0x13C | 2 | | bcdDevice |
+-----------+--------+------------+---------------------------------------------------+
| 0x13E | 1 | | bDeviceClass |
+-----------+--------+------------+---------------------------------------------------+
| 0x13F | 1 | | bDeviceSubClass |
+-----------+--------+------------+---------------------------------------------------+
| 0x140 | 1 | | bDeviceProtocol |
+-----------+--------+------------+---------------------------------------------------+
| 0x141 | 1 | | bConfigurationValue |
+-----------+--------+------------+---------------------------------------------------+
| 0x142 | 1 | | bNumConfigurations |
+-----------+--------+------------+---------------------------------------------------+
| 0x143 | 1 | | bNumInterfaces |
+-----------+--------+------------+---------------------------------------------------+
| 0x144 | | m_0 | From now on each interface is described, all |
2021-03-30 20:00:13 +03:00
| | | | together bNumInterfaces times, with the following |
| | | | 4 fields: |
2019-04-16 05:56:01 +03:00
+-----------+--------+------------+---------------------------------------------------+
| | 1 | | bInterfaceClass |
+-----------+--------+------------+---------------------------------------------------+
| 0x145 | 1 | | bInterfaceSubClass |
+-----------+--------+------------+---------------------------------------------------+
| 0x146 | 1 | | bInterfaceProtocol |
+-----------+--------+------------+---------------------------------------------------+
| 0x147 | 1 | | padding byte for alignment, shall be set to zero |
+-----------+--------+------------+---------------------------------------------------+
| 0xC + | | | The second exported USB device starts at i=1 |
2021-03-30 20:00:13 +03:00
| i*0x138 + | | | with the path field. |
2019-04-16 05:56:01 +03:00
| m_(i-1)*4 | | | |
+-----------+--------+------------+---------------------------------------------------+
2011-08-22 05:52:47 +04:00
2019-04-16 05:56:01 +03:00
OP_REQ_IMPORT:
Request to import (attach) a remote USB device.
2011-08-22 05:52:47 +04:00
2019-04-16 05:56:01 +03:00
+-----------+--------+------------+---------------------------------------------------+
| Offset | Length | Value | Description |
+===========+========+============+===================================================+
2021-03-30 20:00:13 +03:00
| 0 | 2 | | USBIP version |
2019-04-16 05:56:01 +03:00
+-----------+--------+------------+---------------------------------------------------+
| 2 | 2 | 0x8003 | Command code: import a remote USB device. |
+-----------+--------+------------+---------------------------------------------------+
| 4 | 4 | 0x00000000 | Status: unused, shall be set to 0 |
+-----------+--------+------------+---------------------------------------------------+
| 8 | 32 | | busid: the busid of the exported device on the |
| | | | remote host. The possible values are taken |
| | | | from the message field OP_REP_DEVLIST.busid. |
| | | | A string closed with zero, the unused bytes |
| | | | shall be filled with zeros. |
+-----------+--------+------------+---------------------------------------------------+
2011-08-22 05:52:47 +04:00
2019-04-16 05:56:01 +03:00
OP_REP_IMPORT:
Reply to import (attach) a remote USB device.
2011-08-22 05:52:47 +04:00
2019-04-16 05:56:01 +03:00
+-----------+--------+------------+---------------------------------------------------+
| Offset | Length | Value | Description |
+===========+========+============+===================================================+
2021-03-30 20:00:13 +03:00
| 0 | 2 | | USBIP version |
2019-04-16 05:56:01 +03:00
+-----------+--------+------------+---------------------------------------------------+
| 2 | 2 | 0x0003 | Reply code: Reply to import. |
+-----------+--------+------------+---------------------------------------------------+
| 4 | 4 | 0x00000000 | Status: |
| | | | |
| | | | - 0 for OK |
| | | | - 1 for error |
+-----------+--------+------------+---------------------------------------------------+
| 8 | | | From now on comes the details of the imported |
| | | | device, if the previous status field was OK (0), |
| | | | otherwise the reply ends with the status field. |
+-----------+--------+------------+---------------------------------------------------+
| | 256 | | path: Path of the device on the host exporting the|
| | | | USB device, string closed with zero byte, e.g. |
| | | | "/sys/devices/pci0000:00/0000:00:1d.1/usb3/3-2" |
| | | | The unused bytes shall be filled with zero |
| | | | bytes. |
+-----------+--------+------------+---------------------------------------------------+
| 0x108 | 32 | | busid: Bus ID of the exported device, string |
| | | | closed with zero byte, e.g. "3-2". The unused |
| | | | bytes shall be filled with zero bytes. |
+-----------+--------+------------+---------------------------------------------------+
| 0x128 | 4 | | busnum |
+-----------+--------+------------+---------------------------------------------------+
| 0x12C | 4 | | devnum |
+-----------+--------+------------+---------------------------------------------------+
| 0x130 | 4 | | speed |
+-----------+--------+------------+---------------------------------------------------+
| 0x134 | 2 | | idVendor |
+-----------+--------+------------+---------------------------------------------------+
| 0x136 | 2 | | idProduct |
+-----------+--------+------------+---------------------------------------------------+
| 0x138 | 2 | | bcdDevice |
+-----------+--------+------------+---------------------------------------------------+
| 0x139 | 1 | | bDeviceClass |
+-----------+--------+------------+---------------------------------------------------+
| 0x13A | 1 | | bDeviceSubClass |
+-----------+--------+------------+---------------------------------------------------+
| 0x13B | 1 | | bDeviceProtocol |
+-----------+--------+------------+---------------------------------------------------+
| 0x13C | 1 | | bConfigurationValue |
+-----------+--------+------------+---------------------------------------------------+
| 0x13D | 1 | | bNumConfigurations |
+-----------+--------+------------+---------------------------------------------------+
| 0x13E | 1 | | bNumInterfaces |
+-----------+--------+------------+---------------------------------------------------+
2011-08-22 05:52:47 +04:00
2021-03-30 20:00:13 +03:00
The following four commands have a common basic header called
'usbip_header_basic', and their headers, called 'usbip_header' (before
transfer_buffer payload), have the same length, therefore paddings are needed.
2011-08-22 05:52:47 +04:00
2021-03-30 20:00:13 +03:00
usbip_header_basic:
2011-08-22 05:52:47 +04:00
2021-03-30 20:00:13 +03:00
+-----------+--------+---------------------------------------------------+
| Offset | Length | Description |
+===========+========+===================================================+
| 0 | 4 | command |
+-----------+--------+---------------------------------------------------+
| 4 | 4 | seqnum: sequential number that identifies requests|
| | | and corresponding responses; |
| | | incremented per connection |
+-----------+--------+---------------------------------------------------+
| 8 | 4 | devid: specifies a remote USB device uniquely |
| | | instead of busnum and devnum; |
| | | for client (request), this value is |
| | | ((busnum << 16) | devnum); |
| | | for server (response), this shall be set to 0 |
+-----------+--------+---------------------------------------------------+
| 0xC | 4 | direction: |
| | | |
| | | - 0: USBIP_DIR_OUT |
| | | - 1: USBIP_DIR_IN |
| | | |
| | | only used by client, for server this shall be 0 |
+-----------+--------+---------------------------------------------------+
| 0x10 | 4 | ep: endpoint number |
| | | only used by client, for server this shall be 0; |
| | | for UNLINK, this shall be 0 |
+-----------+--------+---------------------------------------------------+
2011-08-22 05:52:47 +04:00
2021-03-30 20:00:13 +03:00
USBIP_CMD_SUBMIT:
Submit an URB
2011-08-22 05:52:47 +04:00
2021-03-30 20:00:13 +03:00
+-----------+--------+---------------------------------------------------+
| Offset | Length | Description |
+===========+========+===================================================+
| 0 | 20 | usbip_header_basic, 'command' shall be 0x00000001 |
+-----------+--------+---------------------------------------------------+
| 0x14 | 4 | transfer_flags: possible values depend on the |
| | | URB transfer_flags (refer to URB doc in |
| | | Documentation/driver-api/usb/URB.rst) |
| | | but with URB_NO_TRANSFER_DMA_MAP masked. Refer to |
| | | function usbip_pack_cmd_submit and function |
| | | tweak_transfer_flags in drivers/usb/usbip/ |
| | | usbip_common.c. The following fields may also ref |
| | | to function usbip_pack_cmd_submit and URB doc |
+-----------+--------+---------------------------------------------------+
| 0x18 | 4 | transfer_buffer_length: |
| | | use URB transfer_buffer_length |
+-----------+--------+---------------------------------------------------+
| 0x1C | 4 | start_frame: use URB start_frame; |
| | | initial frame for ISO transfer; |
| | | shall be set to 0 if not ISO transfer |
+-----------+--------+---------------------------------------------------+
| 0x20 | 4 | number_of_packets: number of ISO packets; |
| | | shall be set to 0xffffffff if not ISO transfer |
+-----------+--------+---------------------------------------------------+
| 0x24 | 4 | interval: maximum time for the request on the |
| | | server-side host controller |
+-----------+--------+---------------------------------------------------+
| 0x28 | 8 | setup: data bytes for USB setup, filled with |
| | | zeros if not used. |
+-----------+--------+---------------------------------------------------+
| 0x30 | n | transfer_buffer. |
| | | If direction is USBIP_DIR_OUT then n equals |
| | | transfer_buffer_length; otherwise n equals 0. |
| | | For ISO transfers the padding between each ISO |
| | | packets is not transmitted. |
+-----------+--------+---------------------------------------------------+
| 0x30+n | m | iso_packet_descriptor |
+-----------+--------+---------------------------------------------------+
2011-08-22 05:52:47 +04:00
2019-04-16 05:56:01 +03:00
USBIP_RET_SUBMIT:
Reply for submitting an URB
2011-08-22 05:52:47 +04:00
2021-03-30 20:00:13 +03:00
+-----------+--------+---------------------------------------------------+
| Offset | Length | Description |
+===========+========+===================================================+
| 0 | 20 | usbip_header_basic, 'command' shall be 0x00000003 |
+-----------+--------+---------------------------------------------------+
| 0x14 | 4 | status: zero for successful URB transaction, |
| | | otherwise some kind of error happened. |
+-----------+--------+---------------------------------------------------+
| 0x18 | 4 | actual_length: number of URB data bytes; |
| | | use URB actual_length |
+-----------+--------+---------------------------------------------------+
| 0x1C | 4 | start_frame: use URB start_frame; |
| | | initial frame for ISO transfer; |
| | | shall be set to 0 if not ISO transfer |
+-----------+--------+---------------------------------------------------+
| 0x20 | 4 | number_of_packets: number of ISO packets; |
| | | shall be set to 0xffffffff if not ISO transfer |
+-----------+--------+---------------------------------------------------+
| 0x24 | 4 | error_count |
+-----------+--------+---------------------------------------------------+
| 0x28 | 8 | padding, shall be set to 0 |
+-----------+--------+---------------------------------------------------+
| 0x30 | n | transfer_buffer. |
| | | If direction is USBIP_DIR_IN then n equals |
| | | actual_length; otherwise n equals 0. |
| | | For ISO transfers the padding between each ISO |
| | | packets is not transmitted. |
+-----------+--------+---------------------------------------------------+
| 0x30+n | m | iso_packet_descriptor |
+-----------+--------+---------------------------------------------------+
2011-08-22 05:52:47 +04:00
2019-04-16 05:56:01 +03:00
USBIP_CMD_UNLINK:
Unlink an URB
2011-08-22 05:52:47 +04:00
2021-03-30 20:00:13 +03:00
+-----------+--------+---------------------------------------------------+
| Offset | Length | Description |
+===========+========+===================================================+
| 0 | 20 | usbip_header_basic, 'command' shall be 0x00000002 |
+-----------+--------+---------------------------------------------------+
| 0x14 | 4 | unlink_seqnum, of the SUBMIT request to unlink |
+-----------+--------+---------------------------------------------------+
| 0x18 | 24 | padding, shall be set to 0 |
+-----------+--------+---------------------------------------------------+
2011-08-22 05:52:47 +04:00
2019-04-16 05:56:01 +03:00
USBIP_RET_UNLINK:
Reply for URB unlink
2011-08-22 05:52:47 +04:00
2021-03-30 20:00:13 +03:00
+-----------+--------+---------------------------------------------------+
| Offset | Length | Description |
+===========+========+===================================================+
| 0 | 20 | usbip_header_basic, 'command' shall be 0x00000004 |
+-----------+--------+---------------------------------------------------+
| 0x14 | 4 | status: This is similar to the status of |
| | | USBIP_RET_SUBMIT (share the same memory offset). |
| | | When UNLINK is successful, status is -ECONNRESET; |
| | | when USBIP_CMD_UNLINK is after USBIP_RET_SUBMIT |
| | | status is 0 |
+-----------+--------+---------------------------------------------------+
| 0x18 | 24 | padding, shall be set to 0 |
+-----------+--------+---------------------------------------------------+
EXAMPLE
=======
The following data is captured from wire with Human Interface Devices (HID)
payload
::
CmdIntrIN: 00000001 00000d05 0001000f 00000001 00000001 00000200 00000040 ffffffff 00000000 00000004 00000000 00000000
CmdIntrOUT: 00000001 00000d06 0001000f 00000000 00000001 00000000 00000040 ffffffff 00000000 00000004 00000000 00000000
ffffffff860008a784ce5ae212376300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
RetIntrOut: 00000003 00000d06 00000000 00000000 00000000 00000000 00000040 ffffffff 00000000 00000000 00000000 00000000
RetIntrIn: 00000003 00000d05 00000000 00000000 00000000 00000000 00000040 ffffffff 00000000 00000000 00000000 00000000
ffffffff860011a784ce5ae2123763612891b1020100000400000000000000000000000000000000000000000000000000000000000000000000000000000000