This page is a documentation of the UART protocol spoken by LEGO EV3 sensors. It was derived from publicly available source code and reverse engineering. This is work in progress.
The EV3 and attached sensors send and receive messages. There are four types of messages:
Each message follows one of the following structures:
The checksum byte is the XOR over the message byte, the info byte (if present), all bytes of the payload, and 0xFF.
The message byte has a special structure: 0bXXLLLYYY. The two most significant bits indicate the type f the message:
XX | Description |
---|---|
00 | System message |
01 | Command message |
10 | Info message |
11 | Date message |
Bits 3-5 of the message byte indicate the length of the payload. To be more precise, the size of the payload is exactly 20bLLL bytes. Thus, the length of a payload must always be a power of 2 and the protocol allows for payloads of at most 128 bytes while actual implementations seem to assume a maximum payload length of 32 bytes. Including the checksum byte, command and data messages thus have a total length of 20bLLL+2 bytes and info messages have a total size of 20bLLL+3 bytes.
System messages have a total length of one. (There may be an exception to that, see the ESC message below.)
Communication with a sensor starts at a speed of 2400 baud. The baud rate can be increased to a higher speed after the initial handshake. The maximum baud rate is reported by the sensor.
Integers larger than 8 bit are encoded using little endian.
Message Byte | Description |
---|---|
0b00000000 | SYNC |
0b00000010 | NACK |
0b00000100 | ACK |
0b00LLL110 | ESC (reserved for future use) |
Message Byte | Payload | Description |
---|---|---|
0b01000000 | T | TYPE: sensor type T is the type of the sensor (1byte) |
0b01001001 | M, V | MODES: sensor modes M+1 is the number of modes supported (1-8) V+1 is the number of modes to be shown (V <= M) |
0b01010010 | SSSS | SPEED: maximum sensor baud rate SSSS (32 bit integer) is the maximum baud rate supported by the sensor |
0b01000011 | M | SELECT: select mode M (0-7) |
0b01LLL100 | <data></data> | WRITE: TODO Note: Has a payload of 0bLLL bytes? |
Message Byte | Info Byte | Payload | Description |
---|---|---|---|
0b10LLLMMM | 0 | <string></string> | NAME: name of mode 0bMMM <string> is an ASCII string, padded with zeros to a length of exactly 20bLLL characters</string> |
0b10011MMM | 1 | LLLL, HHHH | RAW: TODO |
0b10011MMM | 2 | LLLL, HHHH | PCT: TODO |
0b10011MMM | 3 | LLLL, HHHH | SI: TODO |
0b10LLLMMM | 4 | <string></string> | SYMBOL: TODO |
0b10010MMM | 0x80 | S, T, F, D | FORMAT: format of the sensor data in mode 0bMMM S: the number of items T: the data type of the items (see table) F: the number of digits to show (including decimals and the decimal point) D: the number of decimals to show |
Data Type | Description |
---|---|
0 | 8 bit integer |
1 | 16 bit integer |
2 | 32 bit integer |
3 | 32 bit floating point |
Message Byte | Payload | Description |
---|---|---|
0b11LLLMMM | <data></data> | DATA: the sensor return data <data> are the sensor readings for mode 0bMMM, padded to a length of exactly 20bLLL bytes.</data> |
Host | Sensor |
---|---|
baud rate is 2400 | baud rate is 2400 |
send TYPE, MODES, and SPEED | |
per mode, send NAME, RAW, PCT, SI, and FORMAT | |
wait for ACK | send ACK |
send ACK | wait for ACK |
change baud rate | change baud rate |
DATA | |
DATA | |
NACK | |
DATA | |
DATA | |
SELECT | |
DATA | |
DATA | |
NACK | |
DATA | |
DATA |
The MODES command message is optional. A default of M=V=1 is assumed.
The SPEED command message is optional. Default value is unclear.
The info messages for the mode with the highest number must be sent first.
Per mode, NAME must be the first and FORMAT must be the last info message. RAW, PCT, and SI are optional. The following defaults are used when the info message are not sent:
Unclear: The last FORMAT messages indicates default mode? Available material strongly suggests sending mode info in descending order (by mode number) in which case mode 0 is always default.
There must be a delay of at least 10ms between consecutive FORMAT and NAME messages.
A device must send a data message at least every 100ms, but at most every 1ms.
A device should also send a data message after receiving a NACK.
The host should send a NACK every 100ms.
A device should reset if it does not receiving a NACK for 1s. Also, if it does not receive the ACK within 80ms after sending the last FORMAT message, it should reset.
The host may force a reset of the device by not sending any NACKs, e.g. after receiving too many invalid data messages.
If the device does not receive the the initial ACK from the host, the device must reset.
The timeout after which the reset should happen is unclear.