/ bm_rbr_data_msg.cpp
bm_rbr_data_msg.cpp
1 #include "bm_rbr_data_msg.h" 2 #include <math.h> 3 4 namespace BmRbrDataMsg { 5 6 CborError encode(Data &d, uint8_t *cbor_buffer, size_t size, 7 size_t *encoded_len) { 8 CborError err; 9 CborEncoder encoder, map_encoder; 10 cbor_encoder_init(&encoder, cbor_buffer, size, 0); 11 12 do { 13 // Set the unused field to NaN 14 switch (d.sensor_type) { 15 case TEMPERATURE: { 16 d.pressure_deci_bar = NAN; 17 break; 18 } 19 case PRESSURE: { 20 d.temperature_deg_c = NAN; 21 break; 22 } 23 case PRESSURE_AND_TEMPERATURE: { 24 break; 25 } 26 default: { 27 d.temperature_deg_c = NAN; 28 d.pressure_deci_bar = NAN; 29 break; 30 } 31 } 32 33 err = cbor_encoder_create_map(&encoder, &map_encoder, NUM_FIELDS); 34 if (err != CborNoError) { 35 printf("cbor_encoder_create_map failed: %d\n", err); 36 if (err != CborErrorOutOfMemory) { 37 break; 38 } 39 } 40 41 // sensor_header_msg 42 err = SensorHeaderMsg::encode(map_encoder, d.header); 43 if (err != CborNoError) { 44 printf("SensorHeaderMsg::encode failed: %d\n", err); 45 if (err != CborErrorOutOfMemory) { 46 break; 47 } 48 } 49 50 // sensor_type 51 err = cbor_encode_text_stringz(&map_encoder, "sensor_type"); 52 if (err != CborNoError) { 53 printf("cbor_encode_text_stringz failed for sensor_type key: %d\n", err); 54 if (err != CborErrorOutOfMemory) { 55 break; 56 } 57 } 58 err = cbor_encode_uint(&map_encoder, d.sensor_type); 59 if (err != CborNoError) { 60 printf("cbor_encode_double failed for sensor_type value: %d\n", err); 61 if (err != CborErrorOutOfMemory) { 62 break; 63 } 64 } 65 66 // temperature_deg_c 67 err = cbor_encode_text_stringz(&map_encoder, "temperature_deg_c"); 68 if (err != CborNoError) { 69 printf("cbor_encode_text_stringz failed for temperature_deg_c key: %d\n", 70 err); 71 if (err != CborErrorOutOfMemory) { 72 break; 73 } 74 } 75 err = cbor_encode_double(&map_encoder, d.temperature_deg_c); 76 if (err != CborNoError) { 77 printf("cbor_encode_double failed for temperature_deg_c value: %d\n", 78 err); 79 if (err != CborErrorOutOfMemory) { 80 break; 81 } 82 } 83 84 // pressure_deci_bar 85 err = cbor_encode_text_stringz(&map_encoder, "pressure_deci_bar"); 86 if (err != CborNoError) { 87 printf("cbor_encode_text_stringz failed for pressure_deci_bar key: %d\n", 88 err); 89 if (err != CborErrorOutOfMemory) { 90 break; 91 } 92 } 93 err = cbor_encode_double(&map_encoder, d.pressure_deci_bar); 94 if (err != CborNoError) { 95 printf("cbor_encode_double failed for pressure_deci_bar value: %d\n", 96 err); 97 if (err != CborErrorOutOfMemory) { 98 break; 99 } 100 } 101 102 err = cbor_encoder_close_container(&encoder, &map_encoder); 103 if (err == CborNoError) { 104 *encoded_len = cbor_encoder_get_buffer_size(&encoder, cbor_buffer); 105 } else { 106 printf("cbor_encoder_close_container failed: %d\n", err); 107 108 if (err != CborErrorOutOfMemory) { 109 break; 110 } 111 size_t extra_bytes_needed = cbor_encoder_get_extra_bytes_needed(&encoder); 112 printf("extra_bytes_needed: %zu\n", extra_bytes_needed); 113 } 114 } while (0); 115 116 return err; 117 } 118 119 CborError decode(Data &d, const uint8_t *cbor_buffer, size_t size) { 120 CborParser parser; 121 CborValue map; 122 CborError err = cbor_parser_init(cbor_buffer, size, 0, &parser, &map); 123 124 do { 125 if (err != CborNoError) { 126 break; 127 } 128 err = cbor_value_validate_basic(&map); 129 if (err != CborNoError) { 130 break; 131 } 132 if (!cbor_value_is_map(&map)) { 133 err = CborErrorIllegalType; 134 break; 135 } 136 137 size_t num_fields; 138 err = cbor_value_get_map_length(&map, &num_fields); 139 if (err != CborNoError) { 140 break; 141 } 142 if (num_fields != NUM_FIELDS) { 143 err = CborErrorUnknownLength; 144 printf("expected %zu fields but got %zu\n", NUM_FIELDS, num_fields); 145 break; 146 } 147 148 CborValue value; 149 err = cbor_value_enter_container(&map, &value); 150 if (err != CborNoError) { 151 break; 152 } 153 154 // header 155 err = SensorHeaderMsg::decode(value, d.header); 156 if (err != CborNoError) { 157 break; 158 } 159 160 // sensor_type 161 if (!cbor_value_is_text_string(&value)) { 162 err = CborErrorIllegalType; 163 printf("expected string key but got something else\n"); 164 break; 165 } 166 err = cbor_value_advance(&value); 167 if (err != CborNoError) { 168 break; 169 } 170 uint64_t sensor_type; 171 err = cbor_value_get_uint64(&value, &sensor_type); 172 if (err != CborNoError) { 173 break; 174 } 175 d.sensor_type = static_cast<SensorType_t>(sensor_type); 176 err = cbor_value_advance(&value); 177 if (err != CborNoError) { 178 break; 179 } 180 181 // temperature_deg_c 182 if (!cbor_value_is_text_string(&value)) { 183 err = CborErrorIllegalType; 184 printf("expected string key but got something else\n"); 185 break; 186 } 187 err = cbor_value_advance(&value); 188 if (err != CborNoError) { 189 break; 190 } 191 err = cbor_value_get_double(&value, &d.temperature_deg_c); 192 if (err != CborNoError) { 193 break; 194 } 195 err = cbor_value_advance(&value); 196 if (err != CborNoError) { 197 break; 198 } 199 200 // pressure_deci_bar 201 if (!cbor_value_is_text_string(&value)) { 202 err = CborErrorIllegalType; 203 printf("expected string key but got something else\n"); 204 break; 205 } 206 err = cbor_value_advance(&value); 207 if (err != CborNoError) { 208 break; 209 } 210 err = cbor_value_get_double(&value, &d.pressure_deci_bar); 211 if (err != CborNoError) { 212 break; 213 } 214 err = cbor_value_advance(&value); 215 if (err != CborNoError) { 216 break; 217 } 218 219 if (err == CborNoError) { 220 err = cbor_value_leave_container(&map, &value); 221 if (err != CborNoError) { 222 break; 223 } 224 if (!cbor_value_at_end(&map)) { 225 err = CborErrorGarbageAtEnd; 226 break; 227 } 228 } 229 } while (0); 230 231 return err; 232 } 233 234 } // namespace BmRbrDataMsg