This repository has been archived by the owner on Jul 1, 2018. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 39
/
radio_protocol_ng.yaml
344 lines (290 loc) · 9.25 KB
/
radio_protocol_ng.yaml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
- name: uint8_t
repr: unsigned
kind: alien
size: 1
- name: uint16_t
repr: unsigned
kind: alien
size: 2
- name: uint32_t
repr: unsigned
kind: alien
size: 4
- name: uint64_t
repr: unsigned
kind: alien
size: 8
# Radio needs to transmit the following:
# Robot Host
# ---------------------------------------------------
# Telemetry →
# Control signals ←
# Code ←
# Bulk state →
# Debug <->
# Sensor probing <->
# NDL3 ports:
# NDL3_UBJSON_PORT
# Reliable, structured UBJSON data
# Usage:
# Debug
# NDL3_STRING_PORT
# Reliable, unstructured data
# Usage:
# stdout
# stdin?
# NDL3_CODE_PORT
# Reliable, structured binary data
# Usage:
# Code
# Bulk state?
# NDL3_CONFIG_PORT
# Reliable, structured binary data
# Usage:
# start/stop VM
# patch?
# device probing
# NDL3_FAST_PORT
# Unreliable, structured UBJSON data
# Usage:
# Telemetry
# Controls
# UBJSON (reliable) port:
# const TYPE_MEMOIZE_CLEAR 0x00
# const TYPE_MEMOIZE_STRING 0x01
- name: TYPE_MEMOIZE_CLEAR
kind: const
value: 0x00
- name: TYPE_MEMOIZE_STRING
kind: const
value: 0x01
# [
# 123, // type
# { // Only for TYPE_MEMOIZE_STRING
# 123: “str” // Memoize the string “str” with id 123
# …
# }
# ]
# String port:
# Raw, unencapsulated strings for stdin/stdout
# Code port:
# #define ID_SEND_CODE_BLOB 0x00
- name: ID_SEND_CODE_BLOB
kind: const
value: 0x00
# #define ID_GET_TRACE_BLOB 0x01
- name: ID_GET_TRACE_BLOB
kind: const
value: 0x01
- name: code_port
kind: struct
packed: true
slots:
- name: id
type: uint8_t
- name: len
type: uint32_t
- name: data
type: uint8_t[]
# struct code_port (packed) {
# uint8_t id
# uint32_t len
# uint8_t[] data
# }
# Config port:
# #define ID_START_VM
- name: ID_START_VM
kind: const
value: 0x00
# #define ID_STOP_VM
- name: ID_STOP_VM
kind: const
value: 0x01
# #define ID_LOAD_MAIN_THREAD 0x02
- name: ID_LOAD_MAIN_THREAD
kind: const
value: 0x02
# #define ID_CONTROL_UNFREEZE 0x10
- name: ID_CONTROL_UNFREEZE
kind: const
value: 0x10
# #define ID_CONTROL_STOP 0x11
- name: ID_CONTROL_STOP
kind: const
value: 0x11
# #define ID_CONTROL_UNPOWERED 0x12
- name: ID_CONTROL_UNPOWERED
kind: const
value: 0x12
# #define ID_CONTROL_SET_AUTON 0x13
- name: ID_CONTROL_SET_AUTON
kind: const
value: 0x13
# #define ID_CONTROL_SET_TELEOP 0x14
- name: ID_CONTROL_SET_TELEOP
kind: const
value: 0x14
# #define ID_DEVICE_GET_LIST 0x20
- name: ID_DEVICE_GET_LIST
kind: const
value: 0x20
# #define ID_DEVICE_READ_DESCRIPTOR 0x21
- name: ID_DEVICE_READ_DESCRIPTOR
kind: const
value: 0x21
# #define ID_DEVICE_ENABLE_BLINK 0x22
- name: ID_DEVICE_ENABLE_BLINK
kind: const
value: 0x22
- name: device_list_t
kind: struct
packed: true
slots:
- name: count
type: uint32_t
- name: dids
type: uint16_t[]
- name: device_read_descriptor_req_t
kind: struct
packed: true
slots:
- name: did
type: uint64_t
- name: start
type: uint16_t
- name: len
type: uint16_t
- name: LENGTH_AT_LEAST_ONE
kind: const
value: 0x01
- name: device_read_descriptor_resp_t
kind: struct
packed: true
slots:
- name: did
type: uint64_t
- name: data
type: uint8_t[LENGTH_AT_LEAST_ONE]
- name: device_blink_t
kind: struct
packed: true
slots:
- name: did
type: uint64_t
- name: blink_on
type: uint8_t
- name: config_port_data
kind: union
slots:
- name: device_list
type: device_list_t
- name: device_read_descriptor_req
type: device_read_descriptor_req_t
- name: device_read_descriptor_resp
type: device_read_descriptor_resp_t
- name: device_blink
type: device_blink_t
- name: nothing
type: uint8_t
- name: config_port
kind: struct
packed: true
slots:
- name: id
type: uint8_t
- name: data
type: config_port_data
# struct config_port (packed) {
# uint8_t id
# union {
# struct device_list {
# uint32_t count
# uint64_t[] dids
# }
# struct device_read_descriptor_req {
# uint64_t did
# uint16_t start
# uint16_t len
# }
# struct device_read_descriptor_resp {
# uint8_t[] data
# }
# struct device_blink {
# uint8_t blink_on
# uint64_t did
# }
# }
# }
# Fast port:
# const TYPE_JOY_DATA 0x00
# const TYPE_TELEM_DATA 0x01
- name: TYPE_JOY_DATA
kind: const
value: 0x00
- name: TYPE_TELEM_DATA
kind: const
value: 0x01
# [
# nnn, // type
# {
# 123: [1,0,1,…] // Telemetry or joystick, can be repeated
# } // 123 = memoized string
# // array = samples (for telemetry)
# // channel (for joystick)
# ]
# More detailed brain dumps:
# Notes on UBJSON
# UBJSON is only available to Lua. Any state that needs to be available to C cannot be sent via UBJSON (easily). Any data from UBJSON can be condidered “untrusted” (not resistant against tampering from within studencode)
# String memoization
# The purpose of string memoization is to reduce the number of bytes that need to be sent repeatedly. For example, suppose there was a string “joy0-analog” that needed to be sent in every joystick packet. This takes up 11 bytes in every telemetry packet that conveys no additional information after the first time. String memoization solves this by having the host send a unique number and the string to the controller once at the beginning. The string will then be replaced by this number, which will usually take only 1 byte.
# The host can memoize strings sent to the controller. The controller can also send back a TYPE_MEMOIZE_STRING back to the host for e.g. telemetry. IDs may overlap between the two.
# TYPE_MEMOIZE_CLEAR clears both directions
# String port
# This port is directly mapped to stdio. No encapsulation
# printf() from robot appears here
# data written to this port should be made available via scanf, etc.
# Code/trace
# Code is always host-->robot
# Trace is always robot-->host
# Code is not run immediately. Running the code is controlled by the config port.
# How to trigger trace is TBD
# Config
# The majority of host “controlling” the robot happens here. This includes field control logic.
# VM state control
# The host can completely stop execution of any studentcode by sending a stop command. This tears down the VM and frees all of the associated state.
# Start will cause a VM to be created. Standard libraries will be loaded but no studentcode will be.
# Load main thread is used to load the studentcode. The studentcode must have been sent earlier using the code port.
# Replacing the studentcode should work. This needs to be worked out on the runtime dide. Loading studentcode when there is already a studentcode should tear down the student-controlled parts of the VM without rebooting the entire VM.
# Patching will be controlled here. Exact behavior TBD.
# Field control logic
# Field control logic is here (rather than e.g. a UBJSON port) so that it is impossible for students to cheat it.
# There are three stop/run states (unfreeze, stop, unpowered) because of corner-cases with e.g. servos. There are extensive notes on this elsewhere.
# Autonomous and teleop are needed by the C code to block access to the joystick (PiER never did this). It will also be exposed to Lua
# Smartdevice logic
# Smartdevices will be enumerated by the firmware at TBD time. The host can request a list of devices using the get list command. This will return a list of smart device UUIDs.
# The firmware will automatically handle bw allocation and most of the details of communicating with devices. The UI needs to handle human-readable descriptors and binding devices to meaningful names.
# The UI can get descriptions of the devices by reading the descriptor information. See smartdevice spec.
# In order to help identify devices that are already mounted on the robot, the UI can command the LED on the smartdevice to blink.
# Joystick
# Joystick packets contain a number of channels that each contain a number of values. Each individual value can be referred to as <channel name>-<value number>
# For the Xbox 360 joystick, there would be 2 channels: button, analog with 11 and 8 values
# Multiple joysticks can be sent in the same packet
# Telemetry
# Telemetry contains channels that can contain 1 or more samples
# Behavior very similar to joysticks
# Telemetry is batched up and sent at intervals
# Sample exchanges (PC <--> robot);
# config port: 0x01 → (stop VM, reset (almost) all state)
# config port: 0x20 → (get device list)
# config port: ← 0x20 0x01 0x00 0x00 0x00 0xAA 0xBB 0xCC 0xDD 0xEE 0xFF 0x00 0x01
# config port: 0x21 [0xAA … 0x01] 0x00 0x00 0x02 0x00 → (read descriptor length)
# config port: ← 0x21 0x55 0x00
# config port: 0x21 [0xAA … 0x01] 0x00 0x00 0x55 0x00 → (read entire descriptor)
# config port: ← 0x21 …
# config port: 0x00 → (start VM)
# code port: 0x00 0x23 0x01 0xXX 0xXX … → (buffer code)
# config port: 0x02 → (load code into main thread)
# ubjson reliable: [1, {0: “joy0-analog”, 1: “joy0-button”}] → (memoize string)
# config port: 0x10 → (unfreeze)
# ubjson fast: [0, 0: [1,1,0.5, …], 1: [true, false, …]] → (joystick)
# ...