Manchester

Committer:
junhong
Date:
Thu Apr 11 07:52:23 2019 +0000
Revision:
9:7a23184aa9ef
Parent:
8:c1b5893191fe
modified to adopt DALi protocol

Who changed what in which revision?

UserRevisionLine numberNew contents of line
hudakz 0:d5c75b0e5708 1 /*
hudakz 0:d5c75b0e5708 2 ******************************************************************************
hudakz 0:d5c75b0e5708 3 * @file Manchester.cpp
hudakz 0:d5c75b0e5708 4 * @author Zoltan Hudak
hudakz 2:de778df5892c 5 * @version
hudakz 6:7454ad91f714 6 * @date 2017-May-16
hudakz 0:d5c75b0e5708 7 * @brief Manchester code for mbed
hudakz 0:d5c75b0e5708 8 ******************************************************************************
hudakz 0:d5c75b0e5708 9 * @attention
hudakz 0:d5c75b0e5708 10 *
hudakz 0:d5c75b0e5708 11 * <h2><center>&copy; COPYRIGHT(c) 2017 Zoltan Hudak <hudakz@outlook.com>
hudakz 0:d5c75b0e5708 12 *
hudakz 0:d5c75b0e5708 13 * All rights reserved.
hudakz 0:d5c75b0e5708 14
hudakz 0:d5c75b0e5708 15 This program is free software: you can redistribute it and/or modify
hudakz 0:d5c75b0e5708 16 it under the terms of the GNU General Public License as published by
hudakz 0:d5c75b0e5708 17 the Free Software Foundation, either version 3 of the License, or
hudakz 0:d5c75b0e5708 18 (at your option) any later version.
hudakz 0:d5c75b0e5708 19
hudakz 0:d5c75b0e5708 20 This program is distributed in the hope that it will be useful,
hudakz 0:d5c75b0e5708 21 but WITHOUT ANY WARRANTY; without even the implied warranty of
hudakz 0:d5c75b0e5708 22 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
hudakz 0:d5c75b0e5708 23 GNU General Public License for more details.
hudakz 0:d5c75b0e5708 24
hudakz 0:d5c75b0e5708 25 You should have received a copy of the GNU General Public License
hudakz 0:d5c75b0e5708 26 along with this program. If not, see <http://www.gnu.org/licenses/>.
hudakz 0:d5c75b0e5708 27 */
hudakz 5:3b2c7e9fda3f 28 /*
hudakz 7:afd0ee36dcd1 29 This library implements Manchester code according to both IEEE 802.3
hudakz 7:afd0ee36dcd1 30 and G.E. Thomas' conventions.
hudakz 7:afd0ee36dcd1 31 • A '0' is expressed by a high-to-low transition, a '1' by low-to-high transition
hudakz 5:3b2c7e9fda3f 32 in the IEEE 802.3 convention. The reverse is true in the G.E. Thomas' convention.
hudakz 7:afd0ee36dcd1 33 • The transitions which signify '0' or '1' occur at the midpoint of a period.
hudakz 7:afd0ee36dcd1 34 • Transitions at the start of a period are overhead and don't signify data.
hudakz 7:afd0ee36dcd1 35 • Least significant bit is sent first
hudakz 7:afd0ee36dcd1 36 • There is one synchronization pulse at the begin of transmission
hudakz 7:afd0ee36dcd1 37
hudakz 5:3b2c7e9fda3f 38 The IEEE 802.3 convention is used by default.
hudakz 7:afd0ee36dcd1 39 Select a convention to be used by commenting or uncommenting
hudakz 5:3b2c7e9fda3f 40 the line "#define G_E_THOMAS 1" in the Manchester.h header file.
hudakz 5:3b2c7e9fda3f 41 */
hudakz 0:d5c75b0e5708 42 #include "Manchester.h"
junhong 9:7a23184aa9ef 43 #include "mbed-trace/mbed_trace.h"
junhong 9:7a23184aa9ef 44
junhong 9:7a23184aa9ef 45 #undef TRACE_GROUP
junhong 9:7a23184aa9ef 46 #define TRACE_GROUP "Manchester"
hudakz 0:d5c75b0e5708 47
hudakz 0:d5c75b0e5708 48 /**
hudakz 0:d5c75b0e5708 49 * @brief Creates a Manchester object
hudakz 0:d5c75b0e5708 50 * @note
hudakz 0:d5c75b0e5708 51 * @param txPin Pin name of transmitter line
hudakz 0:d5c75b0e5708 52 * rxPin Pin name of receiver line
hudakz 0:d5c75b0e5708 53 * speed Communication bit rate in bits per second
hudakz 3:03109c995123 54 * tol Pulse width tolerance in %
hudakz 0:d5c75b0e5708 55 * @retval
hudakz 0:d5c75b0e5708 56 */
hudakz 3:03109c995123 57 Manchester::Manchester
hudakz 8:c1b5893191fe 58 (
hudakz 8:c1b5893191fe 59 PinName txPin,
hudakz 8:c1b5893191fe 60 PinName rxPin,
hudakz 8:c1b5893191fe 61 uint32_t baudrate, /* = 1200 bps */
hudakz 8:c1b5893191fe 62 uint8_t tol, /* = (+/-)25% */
hudakz 8:c1b5893191fe 63 float rxTimeout /* = 5s */
hudakz 8:c1b5893191fe 64 ) :
hudakz 7:afd0ee36dcd1 65 _tx(txPin),
hudakz 8:c1b5893191fe 66 _rx(rxPin)
hudakz 8:c1b5893191fe 67 {
hudakz 0:d5c75b0e5708 68 _state = IDLE;
hudakz 8:c1b5893191fe 69 _midBitTime = 1000000 / baudrate / 2; // mid-bit time [us]
hudakz 0:d5c75b0e5708 70 _minPulseWidth = (_midBitTime * 2 * (100 - tol)) / 100; // [us]
hudakz 0:d5c75b0e5708 71 _maxPulseWidth = (_midBitTime * 2 * (100 + tol)) / 100; // [us]
hudakz 8:c1b5893191fe 72 _rxTimeout = rxTimeout;
hudakz 0:d5c75b0e5708 73 _rx.disable_irq();
hudakz 0:d5c75b0e5708 74 _rx.rise(callback(this, &Manchester::reception));
hudakz 0:d5c75b0e5708 75 _rx.fall(callback(this, &Manchester::reception));
junhong 9:7a23184aa9ef 76 _preamble = 1; // number of synch_start patterns
junhong 9:7a23184aa9ef 77
junhong 9:7a23184aa9ef 78 tr_debug("_midBitTime = %d", _midBitTime);
junhong 9:7a23184aa9ef 79 tr_debug("_minPulseWidth = %d", _minPulseWidth);
junhong 9:7a23184aa9ef 80 tr_debug("_maxPulseWidth = %d", _maxPulseWidth);
hudakz 5:3b2c7e9fda3f 81 _tx = 0;
hudakz 0:d5c75b0e5708 82 }
hudakz 0:d5c75b0e5708 83
hudakz 0:d5c75b0e5708 84 /**
hudakz 0:d5c75b0e5708 85 * @brief Transmits message
hudakz 0:d5c75b0e5708 86 * @note
hudakz 0:d5c75b0e5708 87 * @param msg Message to transmit
hudakz 0:d5c75b0e5708 88 * @retval
hudakz 0:d5c75b0e5708 89 */
junhong 9:7a23184aa9ef 90 void Manchester::transmit(uint8_t* msg, uint8_t len)
hudakz 8:c1b5893191fe 91 {
hudakz 6:7454ad91f714 92 bool txFinished;
hudakz 0:d5c75b0e5708 93
junhong 9:7a23184aa9ef 94 _data = (char*)msg;
junhong 9:7a23184aa9ef 95 _len = len;
hudakz 0:d5c75b0e5708 96 _state = SYNCH_START;
hudakz 0:d5c75b0e5708 97 _txTicker.attach_us(callback(this, &Manchester::transmission), _midBitTime);
hudakz 0:d5c75b0e5708 98
hudakz 6:7454ad91f714 99 do {
hudakz 0:d5c75b0e5708 100 core_util_critical_section_enter();
hudakz 6:7454ad91f714 101 txFinished = (_state == IDLE);
hudakz 0:d5c75b0e5708 102 core_util_critical_section_exit();
hudakz 8:c1b5893191fe 103 } while (!txFinished);
hudakz 0:d5c75b0e5708 104
hudakz 0:d5c75b0e5708 105 _txTicker.detach();
hudakz 0:d5c75b0e5708 106 }
hudakz 0:d5c75b0e5708 107
hudakz 0:d5c75b0e5708 108 /**
hudakz 0:d5c75b0e5708 109 * @brief ISR handling transmission
hudakz 3:03109c995123 110 * @note Called by _txTicker
hudakz 0:d5c75b0e5708 111 * @param
hudakz 0:d5c75b0e5708 112 * @retval
hudakz 0:d5c75b0e5708 113 */
hudakz 8:c1b5893191fe 114 void Manchester::transmission(void)
hudakz 8:c1b5893191fe 115 {
hudakz 0:d5c75b0e5708 116 static uint8_t encodeByte;
hudakz 2:de778df5892c 117 static size_t byteIndex;
hudakz 0:d5c75b0e5708 118 static uint8_t bitIndex;
hudakz 8:c1b5893191fe 119 static uint8_t counter;
hudakz 0:d5c75b0e5708 120
hudakz 8:c1b5893191fe 121 _timeout.attach_us(callback(this, &Manchester::onTxTimeout), _maxPulseWidth * 4);
hudakz 2:de778df5892c 122
hudakz 8:c1b5893191fe 123 switch (_state)
hudakz 8:c1b5893191fe 124 {
hudakz 8:c1b5893191fe 125 case SYNCH_START:
hudakz 8:c1b5893191fe 126 if (_preamble == 0)
hudakz 8:c1b5893191fe 127 {
hudakz 8:c1b5893191fe 128 byteIndex = 0;
hudakz 8:c1b5893191fe 129 encodeByte = _data[byteIndex];
hudakz 8:c1b5893191fe 130 bitIndex = 0;
hudakz 8:c1b5893191fe 131 _state = SETUP;
hudakz 8:c1b5893191fe 132 break;
hudakz 8:c1b5893191fe 133 }
hudakz 0:d5c75b0e5708 134
hudakz 8:c1b5893191fe 135 _tx = 1; // bring line high to start synch pulse
junhong 9:7a23184aa9ef 136
hudakz 8:c1b5893191fe 137 counter = 0;
hudakz 8:c1b5893191fe 138 _state = SYNCH_NEXT;
hudakz 8:c1b5893191fe 139 break;
hudakz 0:d5c75b0e5708 140
hudakz 8:c1b5893191fe 141 case SYNCH_NEXT:
hudakz 8:c1b5893191fe 142 counter++;
junhong 9:7a23184aa9ef 143 _tx = !_tx;
junhong 9:7a23184aa9ef 144 byteIndex = 0;
junhong 9:7a23184aa9ef 145 encodeByte = _data[byteIndex];
junhong 9:7a23184aa9ef 146 bitIndex = 0;
junhong 9:7a23184aa9ef 147 _state = SETUP;
junhong 9:7a23184aa9ef 148 break;
hudakz 0:d5c75b0e5708 149
hudakz 8:c1b5893191fe 150 case SETUP:
junhong 9:7a23184aa9ef 151 _tx = ((encodeByte >> 7) & 0x01); // setup for next bit to transmit
hudakz 8:c1b5893191fe 152 _state = TRANSITION;
hudakz 8:c1b5893191fe 153 break;
hudakz 0:d5c75b0e5708 154
hudakz 8:c1b5893191fe 155 case TRANSITION:
junhong 9:7a23184aa9ef 156 _tx = !((encodeByte >> 7) & 0x01); // set line appropriately for transition
junhong 9:7a23184aa9ef 157
hudakz 8:c1b5893191fe 158 if (++bitIndex < 8)
hudakz 8:c1b5893191fe 159 {
junhong 9:7a23184aa9ef 160 encodeByte = (encodeByte << 1);
hudakz 0:d5c75b0e5708 161 _state = SETUP;
hudakz 0:d5c75b0e5708 162 }
hudakz 0:d5c75b0e5708 163 else
hudakz 8:c1b5893191fe 164 {
hudakz 8:c1b5893191fe 165 if (++byteIndex < _len)
hudakz 8:c1b5893191fe 166 {
hudakz 8:c1b5893191fe 167 encodeByte = _data[byteIndex];
hudakz 8:c1b5893191fe 168 _state = SETUP;
hudakz 8:c1b5893191fe 169 bitIndex = 0;
hudakz 8:c1b5893191fe 170 }
hudakz 8:c1b5893191fe 171 else
hudakz 8:c1b5893191fe 172 {
hudakz 8:c1b5893191fe 173 counter = 0;
hudakz 8:c1b5893191fe 174 _state = STOP;
hudakz 8:c1b5893191fe 175 }
hudakz 8:c1b5893191fe 176 }
hudakz 8:c1b5893191fe 177 break;
hudakz 0:d5c75b0e5708 178
hudakz 8:c1b5893191fe 179 case STOP:
hudakz 8:c1b5893191fe 180 counter++;
junhong 9:7a23184aa9ef 181 _tx = 0;
junhong 9:7a23184aa9ef 182
junhong 9:7a23184aa9ef 183 if (counter == 4)
hudakz 8:c1b5893191fe 184 _state = COMPLETE;
hudakz 8:c1b5893191fe 185 break;
hudakz 0:d5c75b0e5708 186
hudakz 8:c1b5893191fe 187 case COMPLETE:
hudakz 8:c1b5893191fe 188 _tx = 0;
hudakz 8:c1b5893191fe 189 _state = IDLE;
hudakz 8:c1b5893191fe 190 break;
hudakz 8:c1b5893191fe 191
hudakz 8:c1b5893191fe 192 case IDLE:
hudakz 8:c1b5893191fe 193 default:
hudakz 8:c1b5893191fe 194 _timeout.detach();
hudakz 8:c1b5893191fe 195 return;
hudakz 0:d5c75b0e5708 196 }
hudakz 0:d5c75b0e5708 197 }
hudakz 0:d5c75b0e5708 198
hudakz 0:d5c75b0e5708 199 /**
hudakz 2:de778df5892c 200 * @brief ISR handling 'transmission timeout'
hudakz 2:de778df5892c 201 * @note Called when transmitter is stuck.
hudakz 2:de778df5892c 202 * Signals 'end of transmission' by setting state to IDLE
hudakz 7:afd0ee36dcd1 203 * @param
hudakz 7:afd0ee36dcd1 204 * @retval
hudakz 2:de778df5892c 205 */
hudakz 8:c1b5893191fe 206 void Manchester::onTxTimeout(void)
hudakz 8:c1b5893191fe 207 {
hudakz 2:de778df5892c 208 _timeout.detach();
hudakz 2:de778df5892c 209 _state = IDLE;
hudakz 2:de778df5892c 210 }
hudakz 2:de778df5892c 211
hudakz 2:de778df5892c 212 /**
hudakz 0:d5c75b0e5708 213 * @brief Receives message
hudakz 7:afd0ee36dcd1 214 * @note Waits until a message is received or 'reception timeout' occured
hudakz 1:11292d238e50 215 * @param msg Container to store the received message
hudakz 0:d5c75b0e5708 216 * @retval true On success
hudakz 0:d5c75b0e5708 217 * false Otherwise
hudakz 0:d5c75b0e5708 218 */
junhong 9:7a23184aa9ef 219 bool Manchester::receive(uint8_t *msg, uint8_t *len)
hudakz 8:c1b5893191fe 220 {
hudakz 8:c1b5893191fe 221 bool rxFinished;
hudakz 0:d5c75b0e5708 222
junhong 9:7a23184aa9ef 223 _data = (char*)msg;
junhong 9:7a23184aa9ef 224 _maxLen = *len;
hudakz 0:d5c75b0e5708 225 _state = LISTEN;
hudakz 8:c1b5893191fe 226 _timeout.attach(callback(this, &Manchester::onRxTimeout), _rxTimeout);
hudakz 0:d5c75b0e5708 227 _rx.enable_irq();
hudakz 0:d5c75b0e5708 228
hudakz 6:7454ad91f714 229 do {
hudakz 0:d5c75b0e5708 230 core_util_critical_section_enter();
hudakz 0:d5c75b0e5708 231 rxFinished = ((_state == IDLE) || (_state == ERROR));
hudakz 0:d5c75b0e5708 232 core_util_critical_section_exit();
hudakz 8:c1b5893191fe 233 } while (!rxFinished);
hudakz 0:d5c75b0e5708 234
hudakz 0:d5c75b0e5708 235 _rx.disable_irq();
hudakz 8:c1b5893191fe 236 _timer.stop();
hudakz 8:c1b5893191fe 237 _timeout.detach();
hudakz 0:d5c75b0e5708 238
hudakz 8:c1b5893191fe 239 if (_state == ERROR)
hudakz 8:c1b5893191fe 240 {
junhong 9:7a23184aa9ef 241 len = 0;
hudakz 0:d5c75b0e5708 242 _state = IDLE;
hudakz 0:d5c75b0e5708 243 return false;
hudakz 0:d5c75b0e5708 244 }
hudakz 8:c1b5893191fe 245 else
hudakz 8:c1b5893191fe 246 {
junhong 9:7a23184aa9ef 247 *len = _len;
hudakz 0:d5c75b0e5708 248 return true;
hudakz 0:d5c75b0e5708 249 }
hudakz 0:d5c75b0e5708 250 }
hudakz 0:d5c75b0e5708 251
hudakz 0:d5c75b0e5708 252 /**
hudakz 2:de778df5892c 253 * @brief ISR handling reception
hudakz 2:de778df5892c 254 * @note Called on signal change (rise or fall) on receiver line
hudakz 0:d5c75b0e5708 255 * @param
hudakz 0:d5c75b0e5708 256 * @retval
hudakz 0:d5c75b0e5708 257 */
hudakz 8:c1b5893191fe 258 void Manchester::reception(void)
hudakz 8:c1b5893191fe 259 {
hudakz 0:d5c75b0e5708 260 uint32_t now = us_ticker_read();
hudakz 0:d5c75b0e5708 261 static uint32_t begin;
hudakz 0:d5c75b0e5708 262 uint32_t pulseWidth;
hudakz 0:d5c75b0e5708 263 static uint8_t decodeByte;
hudakz 0:d5c75b0e5708 264 static uint8_t bitIndex;
hudakz 0:d5c75b0e5708 265
hudakz 8:c1b5893191fe 266 switch (_state)
hudakz 8:c1b5893191fe 267 {
hudakz 8:c1b5893191fe 268 case LISTEN:
hudakz 0:d5c75b0e5708 269 begin = now;
junhong 9:7a23184aa9ef 270 if (_rx == 1)
hudakz 8:c1b5893191fe 271 {
hudakz 8:c1b5893191fe 272 _state = SYNCH_START;
hudakz 8:c1b5893191fe 273 }
hudakz 8:c1b5893191fe 274 else
hudakz 8:c1b5893191fe 275 {
junhong 9:7a23184aa9ef 276 tr_err("SYNCH_START: Isn't a SYNCH pulse");
hudakz 8:c1b5893191fe 277 _state = ERROR;
hudakz 8:c1b5893191fe 278 }
hudakz 8:c1b5893191fe 279 break;
hudakz 8:c1b5893191fe 280
hudakz 8:c1b5893191fe 281 case SYNCH_START:
hudakz 8:c1b5893191fe 282 pulseWidth = now - begin;
hudakz 8:c1b5893191fe 283 //printf("%d <= %d <= %d\r\n", (_midBitTime * 2) + _minPulseWidth, pulseWidth, (_midBitTime * 2) + _maxPulseWidth);
hudakz 8:c1b5893191fe 284 if (((_midBitTime * 2) + _minPulseWidth <= pulseWidth) && (pulseWidth <= (_midBitTime * 2) + _maxPulseWidth))
hudakz 8:c1b5893191fe 285 {
hudakz 8:c1b5893191fe 286 begin = now;
hudakz 8:c1b5893191fe 287 _state = SYNCH_NEXT;
hudakz 8:c1b5893191fe 288 }
hudakz 8:c1b5893191fe 289 else
hudakz 8:c1b5893191fe 290 {
junhong 9:7a23184aa9ef 291 tr_err("SYNCH_START: Isn't a SYNCH pulse");
hudakz 8:c1b5893191fe 292 _state = ERROR;
hudakz 8:c1b5893191fe 293 }
hudakz 8:c1b5893191fe 294 break;
hudakz 0:d5c75b0e5708 295
hudakz 8:c1b5893191fe 296 case SYNCH_NEXT:
hudakz 8:c1b5893191fe 297 pulseWidth = now - begin;
hudakz 8:c1b5893191fe 298 //printf("%d <= %d <= %d\r\n", (_midBitTime * 2) + _minPulseWidth, pulseWidth, (_midBitTime * 2) + _maxPulseWidth);
hudakz 8:c1b5893191fe 299 if (((_midBitTime * 2) + _minPulseWidth <= pulseWidth) && (pulseWidth <= (_midBitTime * 2) + _maxPulseWidth))
hudakz 8:c1b5893191fe 300 {
hudakz 8:c1b5893191fe 301 begin = now;
hudakz 8:c1b5893191fe 302 _state = SYNCH_NEXT;
hudakz 8:c1b5893191fe 303 }
hudakz 8:c1b5893191fe 304 else
hudakz 8:c1b5893191fe 305 if ((_minPulseWidth <= pulseWidth) && (pulseWidth <= _maxPulseWidth))
hudakz 8:c1b5893191fe 306 {
hudakz 8:c1b5893191fe 307 begin = now;
hudakz 8:c1b5893191fe 308 decodeByte = 0;
hudakz 8:c1b5893191fe 309 bitIndex = 0;
hudakz 8:c1b5893191fe 310 _len = 0;
hudakz 8:c1b5893191fe 311 decodeByte |= (((_rx == 1) & 0x01) << bitIndex++);
hudakz 8:c1b5893191fe 312 _state = DECODE;
hudakz 8:c1b5893191fe 313 }
hudakz 8:c1b5893191fe 314 break;
hudakz 8:c1b5893191fe 315
hudakz 8:c1b5893191fe 316 case DECODE:
hudakz 8:c1b5893191fe 317 pulseWidth = now - begin;
hudakz 8:c1b5893191fe 318 if ((_minPulseWidth <= pulseWidth) && (pulseWidth <= _maxPulseWidth))
hudakz 8:c1b5893191fe 319 {
hudakz 8:c1b5893191fe 320 begin = now;
hudakz 8:c1b5893191fe 321 decodeByte |= (((_rx == 1) & 0x01) << bitIndex++);
hudakz 8:c1b5893191fe 322 if (bitIndex > 7)
hudakz 8:c1b5893191fe 323 {
hudakz 8:c1b5893191fe 324 _data[_len++] = decodeByte;
hudakz 8:c1b5893191fe 325 if (_len > _maxLen - 1)
hudakz 8:c1b5893191fe 326 _state = ERROR;
hudakz 8:c1b5893191fe 327 else
hudakz 8:c1b5893191fe 328 {
hudakz 8:c1b5893191fe 329 decodeByte = 0;
hudakz 8:c1b5893191fe 330 bitIndex = 0;
hudakz 8:c1b5893191fe 331 }
hudakz 8:c1b5893191fe 332 }
hudakz 8:c1b5893191fe 333 break;
hudakz 8:c1b5893191fe 334 }
hudakz 8:c1b5893191fe 335
hudakz 8:c1b5893191fe 336 if (pulseWidth > _maxPulseWidth)
hudakz 8:c1b5893191fe 337 {
junhong 9:7a23184aa9ef 338 if (_rx == 1)
hudakz 8:c1b5893191fe 339 {
hudakz 8:c1b5893191fe 340 begin = now;
hudakz 8:c1b5893191fe 341 _state = COMPLETE; // End of reception
hudakz 0:d5c75b0e5708 342 }
hudakz 0:d5c75b0e5708 343 }
hudakz 8:c1b5893191fe 344 break;
hudakz 0:d5c75b0e5708 345
hudakz 8:c1b5893191fe 346 case COMPLETE:
hudakz 8:c1b5893191fe 347 pulseWidth = now - begin;
hudakz 8:c1b5893191fe 348 if (pulseWidth > _maxPulseWidth)
hudakz 8:c1b5893191fe 349 {
junhong 9:7a23184aa9ef 350 if (_rx == 0)
hudakz 8:c1b5893191fe 351 {
hudakz 8:c1b5893191fe 352 _state = IDLE; // End of reception
hudakz 8:c1b5893191fe 353 }
hudakz 8:c1b5893191fe 354 }
hudakz 8:c1b5893191fe 355 break;
hudakz 0:d5c75b0e5708 356
hudakz 8:c1b5893191fe 357 case IDLE:
hudakz 8:c1b5893191fe 358 case ERROR:
hudakz 8:c1b5893191fe 359 default:
hudakz 8:c1b5893191fe 360 _timeout.detach();
hudakz 8:c1b5893191fe 361 break;
hudakz 0:d5c75b0e5708 362 }
hudakz 0:d5c75b0e5708 363 }
hudakz 0:d5c75b0e5708 364
hudakz 0:d5c75b0e5708 365 /**
hudakz 7:afd0ee36dcd1 366 * @brief ISR handling 'reception timeout'
hudakz 3:03109c995123 367 * @note Called when receiver line is idle longer than limit.
hudakz 7:afd0ee36dcd1 368 * Signals 'end of reception' by setting state to IDLE
hudakz 2:de778df5892c 369 * or 'timeout error' by setting state to ERROR.
hudakz 7:afd0ee36dcd1 370 * @param
hudakz 7:afd0ee36dcd1 371 * @retval
hudakz 0:d5c75b0e5708 372 */
hudakz 8:c1b5893191fe 373 void Manchester::onRxTimeout(void)
hudakz 8:c1b5893191fe 374 {
hudakz 2:de778df5892c 375 _timeout.detach();
hudakz 0:d5c75b0e5708 376
junhong 9:7a23184aa9ef 377 if ((_state == DECODE) && (_rx == 0))
junhong 9:7a23184aa9ef 378 {
junhong 9:7a23184aa9ef 379 tr_err("rx timeout");
junhong 9:7a23184aa9ef 380 _state = IDLE; // Reception successful
junhong 9:7a23184aa9ef 381 }
junhong 9:7a23184aa9ef 382 else
junhong 9:7a23184aa9ef 383 {
junhong 9:7a23184aa9ef 384 tr_err("reception error");
junhong 9:7a23184aa9ef 385 _state = ERROR; // Reception incomplete
junhong 9:7a23184aa9ef 386 }
hudakz 0:d5c75b0e5708 387 }