HSC2011/Communication/Serial protocol

aus Metalab Wiki, dem offenen Zentrum für meta-disziplinäre Magier und technisch-kreative Enthusiasten.
Zur Navigation springenZur Suche springen

< HSC2011

Serial communication

Both base station and buzzers are capable of communicating on the serial line. Serial communication is ASCII and line based. Most of the serial communication reflects RF commands; the host can send lines that result in an RF packet to be sent, and the device will send a line for every packet it receives.

Every line starts with a letter indicating the type of command being described in the line.

Arguments are either boolean / tristate (y for yes and n for no, z for don't change) or hex encoded; individual commands might implement other argument formats as well.

The commands are grouped in three categories:

RF package commands

This is the typical case of commands and maps directly to an RF package as defined in pktspec.h. The general structure is:

<command letter> <seqnum> <source address> <destination address> <command
specific arguments>

where seqnum is a 1 byte hex sequence number, source and destination address are 8 byte hex values. Both addresses can, as a short cut, be * to indicate the device's own current address or $ to indicate the currently configured base station.

Commands sent to * (or explicitly to the connected device's MAC address) are not put on the air but instead processed as if they were just received over the air (e.g. for controlling the base station's LEDs / keys).

The commands are (the convention with letters is that the capital command is sent first and the minuscle is sent as a response):

  • L: Login; sent by a device on power-on until it is acked. Command specific argument is a 8 byte hex encoded iButton address, if one is connected, otherwise it is filled with nulls. It is also sent after a reset, which happens if an event times out or if it receives an 'X' kill package.

  • l: Acknowledgement for L (no arguments)

  • E: Event sent by the device, arguments are <type> <payload>, where type is b for button press events or u for user event (sent by the VM), and payload are two byte hex. With button events, the payload's lower byte's structure is the same as for the S command's mask part (lowest bit meaning "button 0 down").

  • e: Acknowledgement for e (no arguments)

  • S: Set the state of the device. Command specific arguments are:

    <set rgb> [<r> <g> <b>] <set buzzer> [<buzzer>] <led0>..<led3>
    <eventmaskmask> <eventmask>

    The arguments are defined as follows:

    • set rgb: boolean. if true, set the RGB LED to the three hex byte values in r/g/b
    • set buzzer: boolean. if true, set the buzzer to the frequency in buzzer (2 byte hex encoding Hz), or turn the buzzer off it is 00 00.
    • led0 to 3: four tri-states to turn the respective LEDs on, off, or keep them as they are
    • eventmask: hex byte whose lowest bit represents whether a "button 0 down" should be sent, the next "button 1 down", "button 2 down" and "button 3 down", then "button 0 up" until "button 3 up". Only those bits also present in eventmaskmask are actually set, the rest is kept as it is.
  • s: Acknowledgement for S, returns current state of the device. Custom arguments are:

    <led0>..<led3> <button0>..<button3> <ip> <buzzer> <r> <g> <b> <eventmask>

    The arguments are defined as follows:

    • led0 to 3: four booleans indicating which LEDs are on
    • button0 to 3: four booleans indicating which buttons are pressed (independent of the event mask)
    • ip: current value of the instruction pointer (2 byte hex)
    • buzzer: current vaue of the buzzer in Hz (2 byte hex) or 0 for off
    • r, g, b: hex bytes for red/green/blue part of RGB LED
    • eventmask: as in S
  • V: Set VM status. Arguments are:

    <running> <singlestep> <reset> <set stacksize> [<stacksize>] <set
    interrupt> <set ip> [<ip>] <set sp> [<sp>] <set sfp> [<sfp>] <clear error>
    <clear suspend>

    The arguments are defined as follows:

    • running: tri-state describing whether or not the machine should execute instructions at all
    • singlestep: tri-state describing whether the machine will execute a single instruction and then set the error state to VM_E_SINGLESTEPPED (only used in debugging)
    • reset: boolean; if y, the machine is reset and stopped (memory content stays unchanged, just the internal state is reset)
    • set stacksize / stacksize: if the boolean set stacksize is y, the stack size will be configured to the two byte hex value in stacksize
    • set interrupt: boolean; if y, the machine will continue executing code at the memory address in ip, and continue where it left off afterwards
    • set ip: boolean; if y, the machine will continue executing code at the memory address in ip as if this was the next address (only used in debugging)
    • ip: two byte hex address used by set interrupt and set ip
    • set sp / sp: if the boolean set sp is y, the stack pointer will be set to the two byte hex address in sp (only used in debugging)
    • set sfp / sfp: like set sp / sp for the stack frame pointer
    • clear error: boolean; if y, the error flag gets cleared and the execution continues at the instruction after the instruction that created the error. The behavior of the instruction that caused the error is undefined, which usually means that a memory access failed. (only used for debugging)
    • clear suspend: boolean; if y and the machine is waiting for a delay to end, this will clear the delay and start executing commands again (only used for debugging)
  • v: Acknowledgement for V. Arguments are:

    <running> <singlestep> <suspended> <error> <stacksize> <ip> <sp> <sfp>

    The arguments are defined as follows:

    • running: boolean; y if the machine will execute commands (it might though not do so due to error states)
    • singlestep: boolean; y if the machine is so configured as described in V
    • suspended: boolean; y if the machine is waiting for a delay to end
    • error: single byte hex; error code as described in firmware_vm.h (vm_error_e)
    • stacksize, ip, sp, sfp: two byte hex addresses each, as explained in V
  • W: Write to VM memory. Arguments are:

    <length> <addr> <data>

    The arguments are defined as follows:

    • length: one byte hex value; number of bytes to be written
    • addr: two byte hex value; VM address to write the first byte to
    • data: length bytes hex
  • w: Acknowledgement for W (no arguments)

  • R: Read from VM memory. The arguments <length> <addr> are interpreted as in W.

  • r: Data requested using R. The arguments are <length> <addr> <data> as in W, length and data being simply round-tripped.

Direct control

Commands directly affecting the connected device.

  • M00: List all currently configured addresses.
  • M01 <address>: Set the device mac address to the specified one
  • M02 <address>: Set the base station mac address to the specified one
  • M03: Store the currently configured device mac address to the EEPROM
  • M04: Store the currently configured base station mac address to the EEPROM
  • M05: Set the device mac adress to the base station mac address (aka "enable base station mode"

A command to set promiscuous mode is yet to be implemented.


Empty lines and lines starting with * are ignored by the device. The device may generate such lines for debugging reasons; for example, if the host sends a command unknown to the device, it will response with a * followed by an error message.

Terminal Echo

Commands are echoed back to the PC. The echoes are prefixed with a - character. Terminal echo can be turned on by sending a - character and turned off using the + character. The terminal echo is enabled per default.

Sync Sequence

A line sent to the device that is prefixed with = is echoed back with "=== " before and " ===" after it. This may be used to syncronize the serial communication. A synchronization line showing Pi to 50 decimal digits is sent by the device upon power up.