00001 #pragma once
00002
00003 #include "Crazyradio.h"
00004 #include <cstdint>
00005
00006 static int const CRTP_MAX_DATA_SIZE = 30;
00007 static int const CRTP_MAXSIZE = 31;
00008 #define CHECKSIZE(s) static_assert(sizeof(s) <= CRTP_MAXSIZE, #s " packet is too large");
00009
00010 static int const CRTP_MAXSIZE_RESPONSE = 32;
00011 #define CHECKSIZE_RESPONSE(s) static_assert(sizeof(s) <= CRTP_MAXSIZE_RESPONSE, #s " packet is too large");
00012
00013
00014 struct crtp
00015 {
00016 constexpr crtp(uint8_t port, uint8_t channel)
00017 : channel(channel)
00018 , link(3)
00019 , port(port)
00020 {
00021 }
00022
00023 crtp(uint8_t byte)
00024 {
00025 channel = (byte >> 0) & 0x3;
00026 link = (byte >> 2) & 0x3;
00027 port = (byte >> 4) & 0xF;
00028 }
00029
00030 bool operator==(const crtp& other) const {
00031 return channel == other.channel && port == other.port;
00032 }
00033
00034 uint8_t channel:2;
00035 uint8_t link:2;
00036 uint8_t port:4;
00037 } __attribute__((packed));
00038
00039
00040 typedef struct {
00041 uint8_t size;
00042 union {
00043 struct {
00044 uint8_t header;
00045 uint8_t data[CRTP_MAX_DATA_SIZE];
00046 };
00047 uint8_t raw[CRTP_MAX_DATA_SIZE+1];
00048 };
00049 } crtpPacket_t;
00050
00051
00052 struct crtpConsoleResponse
00053 {
00054 static bool match(const Crazyradio::Ack& response) {
00055 return crtp(response.data[0]) == crtp(0, 0);
00056 }
00057
00058 crtp header;
00059 char text[31];
00060 };
00061 CHECKSIZE_RESPONSE(crtpConsoleResponse)
00062
00063
00064
00065 struct crtpParamTocGetItemResponse;
00066 struct crtpParamTocGetItemRequest
00067 {
00068 crtpParamTocGetItemRequest(
00069 uint8_t id)
00070 : header(2, 0)
00071 , command(0)
00072 , id(id)
00073 {
00074 }
00075
00076 bool operator==(const crtpParamTocGetItemRequest& other) const {
00077 return header == other.header && command == other.command && id == other.id;
00078 }
00079
00080 typedef crtpParamTocGetItemResponse Response;
00081
00082 const crtp header;
00083 const uint8_t command;
00084 uint8_t id;
00085 } __attribute__((packed));
00086 CHECKSIZE(crtpParamTocGetItemRequest)
00087
00088 struct crtpParamTocGetItemResponse
00089 {
00090 static bool match(const Crazyradio::Ack& response) {
00091 return response.size > 5 &&
00092 crtp(response.data[0]) == crtp(2, 0) &&
00093 response.data[1] == 0;
00094 }
00095
00096 crtpParamTocGetItemRequest request;
00097 uint8_t length:2;
00098 uint8_t type:1;
00099 uint8_t sign:1;
00100 uint8_t res0:2;
00101 uint8_t readonly:1;
00102 uint8_t group:1;
00103 char text[28];
00104 } __attribute__((packed));
00105 CHECKSIZE_RESPONSE(crtpParamTocGetItemResponse)
00106
00107 struct crtpParamTocGetInfoResponse;
00108 struct crtpParamTocGetInfoRequest
00109 {
00110 crtpParamTocGetInfoRequest()
00111 : header(2, 0)
00112 , command(1)
00113 {
00114 }
00115
00116 bool operator==(const crtpParamTocGetInfoRequest& other) const {
00117 return header == other.header && command == other.command;
00118 }
00119
00120 typedef crtpParamTocGetInfoResponse Response;
00121
00122 const crtp header;
00123 const uint8_t command;
00124 } __attribute__((packed));
00125 CHECKSIZE(crtpParamTocGetInfoRequest)
00126
00127 struct crtpParamTocGetInfoResponse
00128 {
00129 static bool match(const Crazyradio::Ack& response) {
00130 return response.size == 7 &&
00131 crtp(response.data[0]) == crtp(2, 0) &&
00132 response.data[1] == 1;
00133 }
00134
00135 crtpParamTocGetInfoRequest request;
00136 uint8_t numParam;
00137 uint32_t crc;
00138 } __attribute__((packed));
00139 CHECKSIZE_RESPONSE(crtpParamTocGetInfoResponse)
00140
00141 struct crtpParamValueResponse;
00142 struct crtpParamReadRequest
00143 {
00144 crtpParamReadRequest(
00145 uint8_t id)
00146 : header(2, 1)
00147 , id(id)
00148 {
00149 }
00150
00151 bool operator==(const crtpParamReadRequest& other) const {
00152 return header == other.header && id == other.id;
00153 }
00154
00155 typedef crtpParamValueResponse Response;
00156
00157 const crtp header;
00158 const uint8_t id;
00159 } __attribute__((packed));
00160 CHECKSIZE(crtpParamReadRequest)
00161
00162 template <class T>
00163 struct crtpParamWriteRequest
00164 {
00165 crtpParamWriteRequest(
00166 uint8_t id,
00167 const T& value)
00168 : header(2, 2)
00169 , id(id)
00170 , value(value)
00171 {
00172 }
00173
00174 const crtp header;
00175 const uint8_t id;
00176 const T value;
00177 } __attribute__((packed));
00178 CHECKSIZE(crtpParamWriteRequest<double>)
00179
00180 struct crtpParamValueResponse
00181 {
00182 static bool match(const Crazyradio::Ack& response) {
00183 return response.size > 2 &&
00184 (crtp(response.data[0]) == crtp(2, 1) ||
00185 crtp(response.data[0]) == crtp(2, 2));
00186 }
00187
00188 crtpParamReadRequest request;
00189 union {
00190 uint8_t valueUint8;
00191 int8_t valueInt8;
00192 uint16_t valueUint16;
00193 int16_t valueInt16;
00194 uint32_t valueUint32;
00195 int32_t valueInt32;
00196 float valueFloat;
00197 };
00198 } __attribute__((packed));
00199 CHECKSIZE_RESPONSE(crtpParamValueResponse)
00200
00201
00202 struct crtpParamTocGetItemV2Response;
00203 struct crtpParamTocGetItemV2Request
00204 {
00205 crtpParamTocGetItemV2Request(
00206 uint16_t id)
00207 : header(2, 0)
00208 , command(2)
00209 , id(id)
00210 {
00211 }
00212
00213 bool operator==(const crtpParamTocGetItemV2Request& other) const {
00214 return header == other.header && command == other.command && id == other.id;
00215 }
00216
00217 typedef crtpParamTocGetItemResponse Response;
00218
00219 const crtp header;
00220 const uint8_t command;
00221 uint16_t id;
00222 } __attribute__((packed));
00223 CHECKSIZE(crtpParamTocGetItemV2Request)
00224
00225 struct crtpParamTocGetItemV2Response
00226 {
00227 static bool match(const Crazyradio::Ack& response) {
00228 return response.size > 5 &&
00229 crtp(response.data[0]) == crtp(2, 0) &&
00230 response.data[1] == 2;
00231 }
00232
00233 crtpParamTocGetItemV2Request request;
00234 uint8_t length:2;
00235 uint8_t type:1;
00236 uint8_t sign:1;
00237 uint8_t res0:2;
00238 uint8_t readonly:1;
00239 uint8_t group:1;
00240 char text[27];
00241 } __attribute__((packed));
00242 CHECKSIZE_RESPONSE(crtpParamTocGetItemV2Response)
00243
00244 struct crtpParamTocGetInfoV2Response;
00245 struct crtpParamTocGetInfoV2Request
00246 {
00247 crtpParamTocGetInfoV2Request()
00248 : header(2, 0)
00249 , command(3)
00250 {
00251 }
00252
00253 bool operator==(const crtpParamTocGetInfoV2Request& other) const {
00254 return header == other.header && command == other.command;
00255 }
00256
00257 typedef crtpParamTocGetInfoV2Response Response;
00258
00259 const crtp header;
00260 const uint8_t command;
00261 } __attribute__((packed));
00262 CHECKSIZE(crtpParamTocGetInfoV2Request)
00263
00264 struct crtpParamTocGetInfoV2Response
00265 {
00266 static bool match(const Crazyradio::Ack& response) {
00267 return response.size == 8 &&
00268 crtp(response.data[0]) == crtp(2, 0) &&
00269 response.data[1] == 3;
00270 }
00271
00272 crtpParamTocGetInfoV2Request request;
00273 uint16_t numParam;
00274 uint32_t crc;
00275 } __attribute__((packed));
00276 CHECKSIZE_RESPONSE(crtpParamTocGetInfoV2Response)
00277
00278 struct crtpParamValueV2Response;
00279 struct crtpParamReadV2Request
00280 {
00281 crtpParamReadV2Request(
00282 uint16_t id)
00283 : header(2, 1)
00284 , id(id)
00285 {
00286 }
00287
00288 bool operator==(const crtpParamReadV2Request& other) const {
00289 return header == other.header && id == other.id;
00290 }
00291
00292 typedef crtpParamValueV2Response Response;
00293
00294 const crtp header;
00295 const uint16_t id;
00296 } __attribute__((packed));
00297 CHECKSIZE(crtpParamReadV2Request)
00298
00299 template <class T>
00300 struct crtpParamWriteV2Request
00301 {
00302 crtpParamWriteV2Request(
00303 uint16_t id,
00304 const T& value)
00305 : header(2, 2)
00306 , id(id)
00307 , value(value)
00308 {
00309 }
00310
00311 const crtp header;
00312 const uint16_t id;
00313 const T value;
00314 } __attribute__((packed));
00315 CHECKSIZE(crtpParamWriteV2Request<float>)
00316
00317 struct crtpParamValueV2Response
00318 {
00319 static bool match(const Crazyradio::Ack& response) {
00320 return response.size > 2 &&
00321 (crtp(response.data[0]) == crtp(2, 1) ||
00322 crtp(response.data[0]) == crtp(2, 2));
00323 }
00324
00325 crtpParamReadV2Request request;
00326 uint8_t status;
00327 union {
00328 uint8_t valueUint8;
00329 int8_t valueInt8;
00330 uint16_t valueUint16;
00331 int16_t valueInt16;
00332 uint32_t valueUint32;
00333 int32_t valueInt32;
00334 float valueFloat;
00335 };
00336 } __attribute__((packed));
00337 CHECKSIZE_RESPONSE(crtpParamValueV2Response)
00338
00339
00340
00341 struct crtpSetpointRequest
00342 {
00343 crtpSetpointRequest(
00344 float roll,
00345 float pitch,
00346 float yawrate,
00347 uint16_t thrust)
00348 : header(0x03, 0)
00349 , roll(roll)
00350 , pitch(pitch)
00351 , yawrate(yawrate)
00352 , thrust(thrust)
00353 {
00354 }
00355 const crtp header;
00356 float roll;
00357 float pitch;
00358 float yawrate;
00359 uint16_t thrust;
00360 } __attribute__((packed));
00361 CHECKSIZE(crtpSetpointRequest)
00362
00363
00364
00365 struct crtpMemoryGetNumberRequest
00366 {
00367 crtpMemoryGetNumberRequest()
00368 : header(0x04, 0)
00369 , command(1)
00370 {
00371 }
00372 const crtp header;
00373 const uint8_t command;
00374 } __attribute__((packed));
00375 CHECKSIZE(crtpMemoryGetNumberRequest)
00376
00377 struct crtpMemoryGetNumberResponse
00378 {
00379 static bool match(const Crazyradio::Ack& response) {
00380 return response.size == 3 &&
00381 crtp(response.data[0]) == crtp(4, 0) &&
00382 response.data[1] == 1;
00383 }
00384
00385 crtpMemoryGetNumberRequest request;
00386 uint8_t numberOfMemories;
00387 } __attribute__((packed));
00388 CHECKSIZE_RESPONSE(crtpMemoryGetNumberResponse)
00389
00390 struct crtpMemoryGetInfoRequest
00391 {
00392 crtpMemoryGetInfoRequest(
00393 uint8_t memId)
00394 : header(0x04, 0)
00395 , command(2)
00396 , memId(memId)
00397 {
00398 }
00399 const crtp header;
00400 const uint8_t command;
00401 uint8_t memId;
00402 } __attribute__((packed));
00403 CHECKSIZE(crtpMemoryGetInfoRequest)
00404
00405 enum crtpMemoryType : uint8_t
00406 {
00407 EEPROM = 0x00,
00408 OW = 0x01,
00409 LED12 = 0x10,
00410 LOCO = 0x11,
00411 };
00412
00413 struct crtpMemoryGetInfoResponse
00414 {
00415 static bool match(const Crazyradio::Ack& response) {
00416 return response.size > 2 &&
00417 crtp(response.data[0]) == crtp(4, 0) &&
00418 response.data[1] == 2;
00419 }
00420
00421 crtpMemoryGetInfoRequest request;
00422 crtpMemoryType memType;
00423 uint32_t memSize;
00424 uint64_t memAddr;
00425 } __attribute__((packed));
00426 CHECKSIZE_RESPONSE(crtpMemoryGetInfoResponse)
00427
00428 struct crtpMemoryReadRequest
00429 {
00430 crtpMemoryReadRequest(
00431 uint8_t memId,
00432 uint32_t memAddr,
00433 uint8_t length)
00434 : header(0x04, 1)
00435 , memId(memId)
00436 , memAddr(memAddr)
00437 , length(length)
00438 {
00439 }
00440 const crtp header;
00441 uint8_t memId;
00442 uint32_t memAddr;
00443 uint8_t length;
00444 } __attribute__((packed));
00445 CHECKSIZE(crtpMemoryReadRequest)
00446
00447 struct crtpMemoryReadResponse
00448 {
00449 static bool match(const Crazyradio::Ack& response) {
00450 return response.size > 2 &&
00451 crtp(response.data[0]) == crtp(4, 1);
00452 }
00453
00454 crtp header;
00455 uint8_t memId;
00456 uint32_t memAddr;
00457 uint8_t status;
00458 uint8_t data[24];
00459 } __attribute__((packed));
00460 CHECKSIZE_RESPONSE(crtpMemoryReadResponse)
00461
00462 struct crtpMemoryWriteRequest
00463 {
00464 crtpMemoryWriteRequest(
00465 uint8_t memId,
00466 uint32_t memAddr)
00467 : header(0x04, 2)
00468 , memId(memId)
00469 , memAddr(memAddr)
00470 {
00471 }
00472 const crtp header;
00473 uint8_t memId;
00474 uint32_t memAddr;
00475 uint8_t data[24];
00476 } __attribute__((packed));
00477 CHECKSIZE(crtpMemoryWriteRequest)
00478
00479 struct crtpMemoryWriteResponse
00480 {
00481 static bool match(const Crazyradio::Ack& response) {
00482 return response.size > 2 &&
00483 crtp(response.data[0]) == crtp(4, 2);
00484 }
00485
00486 crtp header;
00487 uint8_t memId;
00488 uint32_t memAddr;
00489 uint8_t status;
00490 } __attribute__((packed));
00491 CHECKSIZE_RESPONSE(crtpMemoryWriteResponse)
00492
00493
00494
00495 struct crtpLogGetInfoResponse;
00496 struct crtpLogGetInfoRequest
00497 {
00498 crtpLogGetInfoRequest()
00499 : header(5, 0)
00500 , command(1)
00501 {
00502 }
00503
00504 bool operator==(const crtpLogGetInfoRequest& other) const {
00505 return header == other.header && command == other.command;
00506 }
00507
00508 typedef crtpLogGetInfoResponse Response;
00509
00510 const crtp header;
00511 const uint8_t command;
00512 } __attribute__((packed));
00513 CHECKSIZE(crtpLogGetInfoRequest)
00514
00515 struct crtpLogGetInfoResponse
00516 {
00517 static bool match(const Crazyradio::Ack& response) {
00518 return response.size == 9 &&
00519 crtp(response.data[0]) == crtp(5, 0) &&
00520 response.data[1] == 1;
00521 }
00522
00523 crtpLogGetInfoRequest request;
00524
00525 uint8_t log_len;
00526
00527 uint32_t log_crc;
00528
00529 uint8_t log_max_packet;
00530
00531 uint8_t log_max_ops;
00532 } __attribute__((packed));
00533 CHECKSIZE_RESPONSE(crtpLogGetInfoResponse)
00534
00535 struct crtpLogGetItemResponse;
00536 struct crtpLogGetItemRequest
00537 {
00538 crtpLogGetItemRequest(uint8_t id)
00539 : header(5, 0)
00540 , command(0)
00541 , id(id)
00542 {
00543 }
00544
00545 bool operator==(const crtpLogGetItemRequest& other) const {
00546 return header == other.header && command == other.command && id == other.id;
00547 }
00548
00549 typedef crtpLogGetItemResponse Response;
00550
00551 const crtp header;
00552 const uint8_t command;
00553 uint8_t id;
00554 } __attribute__((packed));
00555 CHECKSIZE(crtpLogGetItemRequest)
00556
00557 struct crtpLogGetItemResponse
00558 {
00559 static bool match(const Crazyradio::Ack& response) {
00560 return response.size > 5 &&
00561 crtp(response.data[0]) == crtp(5, 0) &&
00562 response.data[1] == 0;
00563 }
00564
00565 crtpLogGetItemRequest request;
00566 uint8_t type;
00567 char text[28];
00568 } __attribute__((packed));
00569 CHECKSIZE_RESPONSE(crtpLogGetItemResponse)
00570
00571 struct logBlockItem {
00572 uint8_t logType;
00573 uint8_t id;
00574 } __attribute__((packed));
00575
00576 struct crtpLogCreateBlockRequest
00577 {
00578 crtpLogCreateBlockRequest()
00579 : header(5, 1)
00580 , command(0)
00581 {
00582 }
00583
00584 const crtp header;
00585 const uint8_t command;
00586 uint8_t id;
00587 logBlockItem items[14];
00588 } __attribute__((packed));
00589 CHECKSIZE(crtpLogCreateBlockRequest)
00590
00591
00592
00593
00594
00595
00596
00597
00598
00599
00600
00601
00602
00603
00604
00605
00606
00607
00608
00609
00610
00611
00612
00613
00614
00615
00616
00617
00618 struct crtpLogStartRequest
00619 {
00620 crtpLogStartRequest(
00621 uint8_t id,
00622 uint8_t period)
00623 : header(5, 1)
00624 , command(3)
00625 , id(id)
00626 , period(period)
00627 {
00628 }
00629
00630 const crtp header;
00631 const uint8_t command;
00632 uint8_t id;
00633 uint8_t period;
00634 } __attribute__((packed));
00635 CHECKSIZE(crtpLogStartRequest)
00636
00637 struct crtpLogStopRequest
00638 {
00639 crtpLogStopRequest(
00640 uint8_t id)
00641 : header(5, 1)
00642 , command(4)
00643 , id(id)
00644 {
00645 }
00646
00647 const crtp header;
00648 const uint8_t command;
00649 uint8_t id;
00650 } __attribute__((packed));
00651 CHECKSIZE(crtpLogStopRequest)
00652
00653 struct crtpLogResetRequest
00654 {
00655 crtpLogResetRequest()
00656 : header(5, 1)
00657 , command(5)
00658 {
00659 }
00660
00661 const crtp header;
00662 const uint8_t command;
00663 } __attribute__((packed));
00664 CHECKSIZE(crtpLogResetRequest)
00665
00666 enum crtpLogControlResult {
00667 crtpLogControlResultOk = 0,
00668 crtpLogControlResultOutOfMemory = 12,
00669 crtpLogControlResultCmdNotFound = 8,
00670 crtpLogControlResultWrongBlockId = 2,
00671 crtpLogControlResultBlockTooLarge = 7,
00672 crtpLogControlResultBlockExists = 17,
00673
00674 };
00675
00676 struct crtpLogControlResponse
00677 {
00678 static bool match(const Crazyradio::Ack& response) {
00679 return response.size == 4 &&
00680 crtp(response.data[0]) == crtp(5, 1);
00681 }
00682
00683 crtp header;
00684 uint8_t command;
00685 uint8_t requestByte1;
00686 uint8_t result;
00687 } __attribute__((packed));
00688 CHECKSIZE_RESPONSE(crtpLogControlResponse)
00689
00690 struct crtpLogDataResponse
00691 {
00692 static bool match(const Crazyradio::Ack& response) {
00693 return response.size > 4 &&
00694 crtp(response.data[0]) == crtp(5, 2);
00695 }
00696
00697 crtp header;
00698 uint8_t blockId;
00699 uint8_t timestampLo;
00700 uint16_t timestampHi;
00701 uint8_t data[26];
00702 } __attribute__((packed));
00703 CHECKSIZE_RESPONSE(crtpLogDataResponse)
00704
00705
00706 struct crtpLogGetInfoV2Response;
00707 struct crtpLogGetInfoV2Request
00708 {
00709 crtpLogGetInfoV2Request()
00710 : header(5, 0)
00711 , command(3)
00712 {
00713 }
00714
00715 bool operator==(const crtpLogGetInfoV2Request& other) const {
00716 return header == other.header && command == other.command;
00717 }
00718
00719 typedef crtpLogGetInfoV2Response Response;
00720
00721 const crtp header;
00722 const uint8_t command;
00723 } __attribute__((packed));
00724 CHECKSIZE(crtpLogGetInfoV2Request)
00725
00726 struct crtpLogGetInfoV2Response
00727 {
00728 static bool match(const Crazyradio::Ack& response) {
00729 return response.size == 10 &&
00730 crtp(response.data[0]) == crtp(5, 0) &&
00731 response.data[1] == 3;
00732 }
00733
00734 crtpLogGetInfoRequest request;
00735
00736 uint16_t log_len;
00737
00738 uint32_t log_crc;
00739
00740 uint8_t log_max_packet;
00741
00742 uint8_t log_max_ops;
00743 } __attribute__((packed));
00744 CHECKSIZE_RESPONSE(crtpLogGetInfoV2Response)
00745
00746 struct crtpLogGetItemV2Response;
00747 struct crtpLogGetItemV2Request
00748 {
00749 crtpLogGetItemV2Request(uint16_t id)
00750 : header(5, 0)
00751 , command(2)
00752 , id(id)
00753 {
00754 }
00755
00756 bool operator==(const crtpLogGetItemV2Request& other) const {
00757 return header == other.header && command == other.command && id == other.id;
00758 }
00759
00760 typedef crtpLogGetItemV2Response Response;
00761
00762 const crtp header;
00763 const uint8_t command;
00764 uint16_t id;
00765 } __attribute__((packed));
00766 CHECKSIZE(crtpLogGetItemV2Request)
00767
00768 struct crtpLogGetItemV2Response
00769 {
00770 static bool match(const Crazyradio::Ack& response) {
00771 return response.size > 6 &&
00772 crtp(response.data[0]) == crtp(5, 0) &&
00773 response.data[1] == 2;
00774 }
00775
00776 crtpLogGetItemV2Request request;
00777 uint8_t type;
00778 char text[27];
00779 } __attribute__((packed));
00780 CHECKSIZE_RESPONSE(crtpLogGetItemV2Response)
00781
00782 struct logBlockItemV2 {
00783 uint8_t logType;
00784 uint16_t id;
00785 } __attribute__((packed));
00786
00787 struct crtpLogCreateBlockV2Request
00788 {
00789 crtpLogCreateBlockV2Request()
00790 : header(5, 1)
00791 , command(6)
00792 {
00793 }
00794
00795 const crtp header;
00796 const uint8_t command;
00797 uint8_t id;
00798 logBlockItemV2 items[9];
00799 } __attribute__((packed));
00800 CHECKSIZE(crtpLogCreateBlockV2Request)
00801
00802
00803
00804
00805 struct crtpExternalPositionUpdate
00806 {
00807 crtpExternalPositionUpdate(
00808 float x,
00809 float y,
00810 float z)
00811 : header(0x06, 0)
00812 , x(x)
00813 , y(y)
00814 , z(z)
00815 {
00816 }
00817 const crtp header;
00818 float x;
00819 float y;
00820 float z;
00821 } __attribute__((packed));
00822 CHECKSIZE(crtpExternalPositionUpdate)
00823
00824 struct crtpExternalPositionPacked
00825 {
00826 crtpExternalPositionPacked()
00827 : header(0x06, 2)
00828 {
00829 }
00830 const crtp header;
00831 struct {
00832 uint8_t id;
00833 int16_t x;
00834 int16_t y;
00835 int16_t z;
00836 } __attribute__((packed)) positions[4];
00837 } __attribute__((packed));
00838 CHECKSIZE(crtpExternalPositionPacked)
00839
00840 struct crtpStopRequest
00841 {
00842 crtpStopRequest();
00843 const crtp header;
00844 uint8_t type;
00845 } __attribute__((packed));
00846 CHECKSIZE(crtpStopRequest)
00847
00848 struct crtpHoverSetpointRequest
00849 {
00850 crtpHoverSetpointRequest(
00851 float vx,
00852 float vy,
00853 float yawrate,
00854 float zDistance);
00855 const crtp header;
00856 uint8_t type;
00857 float vx;
00858 float vy;
00859 float yawrate;
00860 float zDistance;
00861 } __attribute__((packed));
00862 CHECKSIZE(crtpHoverSetpointRequest)
00863
00864 struct crtpPositionSetpointRequest
00865 {
00866 crtpPositionSetpointRequest(
00867 float x,
00868 float y,
00869 float z,
00870 float yaw);
00871 const crtp header;
00872 uint8_t type;
00873 float x;
00874 float y;
00875 float z;
00876 float yaw;
00877 } __attribute__((packed));
00878 CHECKSIZE(crtpPositionSetpointRequest)
00879
00880
00881
00882 struct crtpFullStateSetpointRequest
00883 {
00884 crtpFullStateSetpointRequest(
00885 float x, float y, float z,
00886 float vx, float vy, float vz,
00887 float ax, float ay, float az,
00888 float qx, float qy, float qz, float qw,
00889 float rollRate, float pitchRate, float yawRate);
00890 const crtp header;
00891 uint8_t type;
00892 int16_t x;
00893 int16_t y;
00894 int16_t z;
00895 int16_t vx;
00896 int16_t vy;
00897 int16_t vz;
00898 int16_t ax;
00899 int16_t ay;
00900 int16_t az;
00901 int32_t quat;
00902 int16_t omegax;
00903 int16_t omegay;
00904 int16_t omegaz;
00905 } __attribute__((packed));
00906 CHECKSIZE(crtpFullStateSetpointRequest)
00907
00908
00909
00910 struct crtpCommanderHighLevelSetGroupMaskRequest
00911 {
00912 crtpCommanderHighLevelSetGroupMaskRequest(
00913 uint8_t groupMask)
00914 : header(0x08, 0)
00915 , command(0)
00916 , groupMask(groupMask)
00917 {
00918 }
00919
00920 const crtp header;
00921 const uint8_t command;
00922 uint8_t groupMask;
00923 } __attribute__((packed));
00924 CHECKSIZE(crtpCommanderHighLevelSetGroupMaskRequest)
00925
00926 struct crtpCommanderHighLevelTakeoffRequest
00927 {
00928 crtpCommanderHighLevelTakeoffRequest(
00929 uint8_t groupMask,
00930 float height,
00931 float duration)
00932 : header(0x08, 0)
00933 , command(1)
00934 , groupMask(groupMask)
00935 , height(height)
00936 , duration(duration)
00937 {
00938 }
00939
00940 const crtp header;
00941 const uint8_t command;
00942 uint8_t groupMask;
00943 float height;
00944 float duration;
00945 } __attribute__((packed));
00946 CHECKSIZE(crtpCommanderHighLevelTakeoffRequest)
00947
00948 struct crtpCommanderHighLevelLandRequest
00949 {
00950 crtpCommanderHighLevelLandRequest(
00951 uint8_t groupMask,
00952 float height,
00953 float duration)
00954 : header(0x08, 0)
00955 , command(2)
00956 , groupMask(groupMask)
00957 , height(height)
00958 , duration(duration)
00959 {
00960 }
00961
00962 const crtp header;
00963 const uint8_t command;
00964 uint8_t groupMask;
00965 float height;
00966 float duration;
00967 } __attribute__((packed));
00968 CHECKSIZE(crtpCommanderHighLevelLandRequest)
00969
00970 struct crtpCommanderHighLevelStopRequest
00971 {
00972 crtpCommanderHighLevelStopRequest(
00973 uint8_t groupMask)
00974 : header(0x08, 0)
00975 , command(3)
00976 , groupMask(groupMask)
00977 {
00978 }
00979
00980 const crtp header;
00981 const uint8_t command;
00982 uint8_t groupMask;
00983 } __attribute__((packed));
00984 CHECKSIZE(crtpCommanderHighLevelStopRequest)
00985
00986 struct crtpCommanderHighLevelGoToRequest
00987 {
00988 crtpCommanderHighLevelGoToRequest(
00989 uint8_t groupMask,
00990 bool relative,
00991 float x,
00992 float y,
00993 float z,
00994 float yaw,
00995 float duration)
00996 : header(0x08, 0)
00997 , command(4)
00998 , groupMask(groupMask)
00999 , relative(relative)
01000 , x(x)
01001 , y(y)
01002 , z(z)
01003 , yaw(yaw)
01004 , duration(duration)
01005 {
01006 }
01007
01008 const crtp header;
01009 const uint8_t command;
01010 uint8_t groupMask;
01011 uint8_t relative;
01012 float x;
01013 float y;
01014 float z;
01015 float yaw;
01016 float duration;
01017 } __attribute__((packed));
01018 CHECKSIZE(crtpCommanderHighLevelGoToRequest)
01019
01020 struct crtpCommanderHighLevelStartTrajectoryRequest
01021 {
01022 crtpCommanderHighLevelStartTrajectoryRequest(
01023 uint8_t groupMask,
01024 bool relative,
01025 bool reversed,
01026 uint8_t trajectoryId,
01027 float timescale)
01028 : header(0x08, 0)
01029 , command(5)
01030 , groupMask(groupMask)
01031 , relative(relative)
01032 , reversed(reversed)
01033 , trajectoryId(trajectoryId)
01034 , timescale(timescale)
01035 {
01036 }
01037
01038 const crtp header;
01039 const uint8_t command;
01040 uint8_t groupMask;
01041 uint8_t relative;
01042 uint8_t reversed;
01043 uint8_t trajectoryId;
01044 float timescale;
01045 } __attribute__((packed));
01046 CHECKSIZE(crtpCommanderHighLevelStartTrajectoryRequest)
01047
01048 enum TrajectoryLocation_e {
01049 TRAJECTORY_LOCATION_INVALID = 0,
01050 TRAJECTORY_LOCATION_MEM = 1,
01051
01052 };
01053
01054 enum TrajectoryType_e {
01055 TRAJECTORY_TYPE_POLY4D = 0,
01056
01057 };
01058
01059 struct trajectoryDescription
01060 {
01061 uint8_t trajectoryLocation;
01062 uint8_t trajectoryType;
01063 union
01064 {
01065 struct {
01066 uint32_t offset;
01067 uint8_t n_pieces;
01068 } __attribute__((packed)) mem;
01069 } trajectoryIdentifier;
01070 } __attribute__((packed));
01071
01072 struct crtpCommanderHighLevelDefineTrajectoryRequest
01073 {
01074 crtpCommanderHighLevelDefineTrajectoryRequest(
01075 uint8_t trajectoryId)
01076 : header(0x08, 0)
01077 , command(6)
01078 , trajectoryId(trajectoryId)
01079 {
01080 }
01081
01082 const crtp header;
01083 const uint8_t command;
01084 uint8_t trajectoryId;
01085 struct trajectoryDescription description;
01086 } __attribute__((packed));
01087 CHECKSIZE(crtpCommanderHighLevelDefineTrajectoryRequest)
01088
01089
01090
01091 typedef uint16_t fp16_t;
01092 typedef int16_t posFixed16_t;
01093 typedef struct posFixed24_t
01094 {
01095 uint8_t low;
01096 uint8_t middle;
01097 uint8_t high;
01098 } posFixed24_t;
01099
01100 struct data_mocap {
01101 struct {
01102 uint8_t id;
01103 posFixed24_t x;
01104 posFixed24_t y;
01105 posFixed24_t z;
01106 uint32_t quat;
01107 } __attribute__((packed)) pose[2];
01108 } __attribute__((packed));
01109
01110 struct crtpPosExtBringup
01111 {
01112 crtpPosExtBringup()
01113 : header(11, 1)
01114 {
01115 data.pose[0].id = 0;
01116 data.pose[1].id = 0;
01117 }
01118
01119 const crtp header;
01120 struct data_mocap data;
01121 } __attribute__((packed));
01122 CHECKSIZE(crtpPosExtBringup)
01123
01124
01125
01126 struct crtpGetProtocolVersionRequest
01127 {
01128 crtpGetProtocolVersionRequest()
01129 : header(0x0D, 1)
01130 {
01131 }
01132
01133 const crtp header;
01134 const uint8_t cmd = 0;
01135 } __attribute__((packed));
01136 CHECKSIZE(crtpGetProtocolVersionRequest)
01137
01138 struct crtpGetProtocolVersionResponse
01139 {
01140 crtpGetProtocolVersionRequest request;
01141 int version;
01142 } __attribute__((packed));
01143 CHECKSIZE_RESPONSE(crtpGetProtocolVersionResponse)
01144
01145 struct crtpGetFirmwareVersionRequest
01146 {
01147 crtpGetFirmwareVersionRequest()
01148 : header(0x0D, 1)
01149 {
01150 }
01151
01152 const crtp header;
01153 const uint8_t cmd = 1;
01154 } __attribute__((packed));
01155 CHECKSIZE(crtpGetProtocolVersionRequest)
01156
01157 struct crtpGetFirmwareVersionResponse
01158 {
01159 crtpGetFirmwareVersionRequest request;
01160 char version[30];
01161 } __attribute__((packed));
01162 CHECKSIZE_RESPONSE(crtpGetFirmwareVersionResponse)
01163
01164 struct crtpGetDeviceTypeNameRequest
01165 {
01166 crtpGetDeviceTypeNameRequest()
01167 : header(0x0D, 1)
01168 {
01169 }
01170
01171 const crtp header;
01172 const uint8_t cmd = 2;
01173 } __attribute__((packed));
01174 CHECKSIZE(crtpGetProtocolVersionRequest)
01175
01176 struct crtpGetDeviceTypeNameResponse
01177 {
01178 crtpGetDeviceTypeNameRequest request;
01179 char name[30];
01180 } __attribute__((packed));
01181 CHECKSIZE_RESPONSE(crtpGetDeviceTypeNameResponse)
01182
01183
01184 struct crtpPlatformRSSIAck
01185 {
01186 static bool match(const Crazyradio::Ack& response) {
01187 return crtp(response.data[0]) == crtp(15, 3);
01188 }
01189
01190 crtp header;
01191 uint8_t reserved;
01192 uint8_t rssi;
01193 };
01194 CHECKSIZE_RESPONSE(crtpPlatformRSSIAck)