USB Command Protocol

Structure of a command block

0000000: xx xx xx xx yy yy yy yy - 00 00 00 00 00 00 00 00
0000010: 00 00 00 00 00 00 00 00 - 00 00 00 00 00 00 00 00
0000020: 00 00 00 00 00 00 00 00 - 00 00 00 00 00 00 00 00
0000030: 00 00 00 00 00 00 00 00 - 00 00 00 00 00 00 00 00
0000040: 02 00 00 00 UU 00 cc VV - xx xx xx xx SS SS SS SS
0000050: ... (payload/arguments)
        

xx xx xx xx : length (word)

yy yy yy yy : cmd3 (word)

UU : cmd1 (byte)

VV : cmd2 (byte)

xx xx xx xx : Length (again)

SS SS SS SS : sequence number (word)

cc : must be zero in old-style protocol. In the new protocol, this byte must contain 0x10 for commands with cmd3=0x201, 0x20 for commands with cmd3=0x202.

  • length is the length of the block, excluding the first 0x40 bytes in block, and is never less than 0x10.

  • cmd1 and cmd2 are each a single byte

  • cmd3 is a word

  • Sequence number is a word, sent back in command reply. This may have more meaning than meets the eye; for example, the last byte is nearly always zero, and similar commands tend to have the same last two bytes in this field.

USB arguments:

  • value is always 0x10

  • length is TOTAL length (0x54 in example below)

Example command block: Disk info request

0000000: 14 00 00 00 01 02 00 00-00 00 00 00 00 00 00 00 ................
0000010: 00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00 ................
0000020: 00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00 ................
0000030: 00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00 ................
0000040: 02 00 00 00 09 00 00 11-14 00 00 00 78 56 34 12 ............xV4.
0000050: 44 3A 5C 00                                     D:\.
        

Structure of a response block

A normal response block will be at least 0x54 bytes long.

0000 00 00 00 00 yy yy 00 00 00 00 00 00 00 00 00 00 ................
0010 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
0020 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
0030 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
0000 02 00 00 00 UU 00 00 VV xx xx xx xx SS SS SS SS ......."........
0010 kk kk kk kk                                     ....
        
  • yyyy will contain an altered copy of cmd3. The high-order byte of cmd3 will be incremented from 2 to 3 (0x2010x301, 0x2020x302).

  • UU will contain a copy of cmd1.

  • VV will contain an altered copy of cmd2, incremented by 0x10 (0x110x21, 0x120x22).

  • The first word of the response block will not contain the length

  • xxxxxxxx will contain the length as a low-endian 32-bit integer at 0x48. This is the length of the useful information, i.e. (total block length)-0x40.

  • SSSSSSSS at 0x4c is just a copy of the word that was sent to the camera in this location; it can be used to match a response to the command that elicited it.

  • kkkkkkkk at 0x50 seems to be a status code; it will be zero if the command succeeded.

Here is an example of a successful response of 0x58 bytes; there is a word of information after the status code.

0000 00 00 00 00 01 03 00 00 00 00 00 00 00 00 00 00 ................
0010 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
0020 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
0030 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
0000 02 00 00 00 0a 00 00 22 18 00 00 00 a4 f4 d6 00 ......."........
0010 00 00 00 00 06 00 00 20                         .......
        

Responses of variable length (those where cmd3 is 0x202 rather than 0x201) are handled differently. For these, the first response will have length 0x40 and contain only the length of the variable response. Here is an example

00000000 00 00 00 00 02 03 CF 1F-0D 00 00 00 00 00 00 00 ................
00000010 00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00 ................
00000020 00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00 ................
00000030 00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00 ................
        

Here we must read 0x00001fcf = 8143 bytes, which will come in unformatted blocks, to be read in chunks as described below.

When a response is greater than 0x40 in length (i.e. almost all responses), it must be read in multiple operations. First read the largest subset divisible by 0x40, then a short read with the remainder. The longest bulk reads will be to download images and thumbnails, but generally it's not a good idea to read more than 0x1400 bytes. The first read may need to be split into shorter operations. To read a response of length bytes,

#define MAX_BULK_XFER 0x1400
do {
  if(length - bytes_read >MAX_BULK_XFER)
    read_chunk = MAX_BULK_XFER;
  else if(length - bytes_read >0x40)
    read_chunk = (length - bytes_read) / 0x40 * 0x40;
  else
    read_chunk = length - bytes_read;
  actually_read = usb_bulk_read(handle, CAMERA_BULK_READ_EP,
                                buffer + bytes_read,
                                read_chunk, USB_TIMEOUT);
  if(actually_read != read_chunk)
    error;
  bytes_read += read_chunk;
} while(bytes_read <length);
        

Status Codes

A status code is returned in the word at 0x50 in the response. Here is a list of known status codes.

CodeMeaning

0x00000000

Success. This is the code most commonly seen.

0x02000022

File not found

0x02000029

File was protected

0x0200002a

Compact Flash card full (on set transfer mode and release shutter)

0x02000081

EOS lock keys failed, e.g. shutter release is half-depressed or camera is in review or menu mode.

0x02000082

EOS unlock keys failed, e.g. tried to unlock keys when they weren't locked to begin with.

0x02000085

camera control initialization failed.

Couldn't extend lens (on G2)

Camera was left in camera control mode

For D60: we just filled the CF card (on next camera control initialization; power cycle clears this)

0x02000086

Path not found or invalid parameters. Indicates either that the pathname wasn't found, e.g. for Get Directory, or that the command block was in error, e.g. the length wasn't correct, or the command for Set File Attributes had only one string, rather than a pathname followed by a filename.

0x00000086

Returned by camera in newer protocol (e.g. EOS 20D) from Unlock keys when keys weren't locked.

0x02000087

No Compact Flash card