First class data visualization and communication library with embedded devices. Code is maintained at github.com/Overdrivr/Telemetry
Dependents: telemetry_car_demo telemetry_demo_FRDM-TFC telemetry_example_01 telemetry_indexed_data_demo ... more
framing.cpp
00001 #include "framing.h" 00002 00003 typedef enum _state 00004 { 00005 IDLE, // No incoming frame is in process 00006 ESCAPING, // incoming frame in process, next character to be escaped 00007 ACTIVE // frame in process 00008 } _state ; 00009 00010 typedef struct storage storage; 00011 struct storage 00012 { 00013 uint8_t * ptr; 00014 uint32_t size; 00015 uint32_t cursor; 00016 00017 }; 00018 00019 static storage incomingStorage; 00020 static storage outgoingStorage; 00021 00022 int8_t safe_append(storage * s, uint8_t byte); 00023 00024 static uint8_t SOF_; 00025 static uint8_t EOF_; 00026 static uint8_t ESC_; 00027 00028 static _state incoming_state; 00029 00030 void (*on_incoming_frame_cb)(uint8_t * storage, uint32_t occupiedSize); 00031 void (*on_error_cb)(int32_t errCode); 00032 00033 void initialize_framing() 00034 { 00035 incomingStorage.ptr = NULL; 00036 outgoingStorage.ptr = NULL; 00037 00038 incomingStorage.size = 0; 00039 outgoingStorage.size = 0; 00040 00041 incomingStorage.cursor = 0; 00042 incomingStorage.cursor = 0; 00043 00044 SOF_ = 0xF7; 00045 EOF_ = 0x7F; 00046 ESC_ = 0x7D; 00047 00048 incoming_state = IDLE; 00049 } 00050 00051 void outgoing_storage(uint8_t * buf, uint32_t bufSize) 00052 { 00053 outgoingStorage.ptr = buf; 00054 outgoingStorage.size = bufSize; 00055 } 00056 00057 void begin() 00058 { 00059 if(outgoingStorage.size == 0 || outgoingStorage.ptr == NULL) 00060 return; 00061 00062 outgoingStorage.cursor = 0; 00063 00064 // Should not fail 00065 safe_append(&outgoingStorage,SOF_); 00066 } 00067 00068 void append(uint8_t byte) 00069 { 00070 if(outgoingStorage.size == 0 || outgoingStorage.ptr == NULL) 00071 return; 00072 00073 // byte == to flag, need to escape it 00074 if(byte == SOF_ || byte == EOF_ || byte == ESC_) 00075 { 00076 if(!safe_append(&outgoingStorage,ESC_)) 00077 return; 00078 } 00079 00080 if(!safe_append(&outgoingStorage,byte)) 00081 return; 00082 } 00083 00084 void append2(uint16_t twobytes) 00085 { 00086 uint8_t * ptr = (uint8_t*)(&twobytes); 00087 append(ptr[0]); 00088 append(ptr[1]); 00089 } 00090 00091 void append4(uint32_t fourbytes) 00092 { 00093 uint8_t * ptr = (uint8_t*)(&fourbytes); 00094 append(ptr[0]); 00095 append(ptr[1]); 00096 append(ptr[2]); 00097 append(ptr[3]); 00098 } 00099 00100 uint32_t end() 00101 { 00102 if(outgoingStorage.size == 0 || outgoingStorage.ptr == NULL) 00103 return 0; 00104 00105 if(!safe_append(&outgoingStorage,EOF_)) 00106 return 0; 00107 00108 return outgoingStorage.cursor; 00109 } 00110 00111 void incoming_storage(uint8_t * buf, uint32_t bufSize) 00112 { 00113 incomingStorage.ptr = buf; 00114 incomingStorage.size = bufSize; 00115 } 00116 00117 void set_on_incoming_frame(void (*callback)(uint8_t * storage, uint32_t occupiedSize)) 00118 { 00119 on_incoming_frame_cb = callback; 00120 } 00121 00122 void set_on_incoming_error(void (*callback)(int32_t errCode)) 00123 { 00124 on_error_cb = callback; 00125 } 00126 00127 void feed(uint8_t byte) 00128 { 00129 if(incomingStorage.size == 0 || incomingStorage.ptr == NULL) 00130 return; 00131 00132 if(incoming_state == ESCAPING) 00133 { 00134 if(!safe_append(&incomingStorage,byte)) 00135 { 00136 incoming_state = IDLE; 00137 return; 00138 } 00139 incoming_state = ACTIVE; 00140 return; 00141 } 00142 00143 if(byte == SOF_) 00144 { 00145 incoming_state = ACTIVE; 00146 incomingStorage.cursor = 0; 00147 return; 00148 } 00149 00150 if(incoming_state == ACTIVE) 00151 { 00152 if(byte == EOF_) 00153 { 00154 incoming_state = IDLE; 00155 on_incoming_frame_cb(incomingStorage.ptr, incomingStorage.cursor); 00156 } 00157 // Escape next character 00158 else if(byte == ESC_) 00159 { 00160 incoming_state = ESCAPING; 00161 } 00162 else 00163 { 00164 if(!safe_append(&incomingStorage,byte)) 00165 { 00166 incoming_state = IDLE; 00167 return; 00168 } 00169 incoming_state = ACTIVE; 00170 } 00171 } 00172 } 00173 00174 int8_t safe_append(storage * s, uint8_t byte) 00175 { 00176 // Not enough space for 1 more character 00177 if(s->cursor + 1 >= s->size) 00178 return 0; 00179 00180 s->ptr[s->cursor++] = byte; 00181 00182 return 1; 00183 }
Generated on Wed Jul 13 2022 21:24:00 by 1.7.2