Driver for Spektrum (tm) serial receiver, for radio controlled helicopters etc.
spektRx.c@0:80f1104f405a, 2011-10-25 (annotated)
- Committer:
- offroad
- Date:
- Tue Oct 25 18:15:55 2011 +0000
- Revision:
- 0:80f1104f405a
Initial release.
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
offroad | 0:80f1104f405a | 1 | #include "mbed.h" |
offroad | 0:80f1104f405a | 2 | #include "spektRx.h" |
offroad | 0:80f1104f405a | 3 | |
offroad | 0:80f1104f405a | 4 | #define NUM_CHAN (7) |
offroad | 0:80f1104f405a | 5 | #define NUM_BYTES_IN_FRAME (2*NUM_CHAN+2) |
offroad | 0:80f1104f405a | 6 | |
offroad | 0:80f1104f405a | 7 | void spektRx_init(spektRx_t* self){ |
offroad | 0:80f1104f405a | 8 | self -> state = 0; |
offroad | 0:80f1104f405a | 9 | self -> valid = false; |
offroad | 0:80f1104f405a | 10 | self -> frameNum = 0L; |
offroad | 0:80f1104f405a | 11 | } |
offroad | 0:80f1104f405a | 12 | |
offroad | 0:80f1104f405a | 13 | bool spektRx_hasValidFrame(spektRx_t* self){ |
offroad | 0:80f1104f405a | 14 | return self->valid; |
offroad | 0:80f1104f405a | 15 | } |
offroad | 0:80f1104f405a | 16 | |
offroad | 0:80f1104f405a | 17 | void spektRx_runChar(spektRx_t* self, unsigned char c){ |
offroad | 0:80f1104f405a | 18 | switch(self->state){ |
offroad | 0:80f1104f405a | 19 | case 0: /* new frame cycle */ |
offroad | 0:80f1104f405a | 20 | /* first preamble byte received: now expect 2nd preamble byte */ |
offroad | 0:80f1104f405a | 21 | self->state = (c == 0x03) ? 1 : 0; |
offroad | 0:80f1104f405a | 22 | break; |
offroad | 0:80f1104f405a | 23 | |
offroad | 0:80f1104f405a | 24 | case 1: |
offroad | 0:80f1104f405a | 25 | /* 2nd preamble byte received: Now expect first data byte */ |
offroad | 0:80f1104f405a | 26 | self->state = (c == 0x01) ? 2 : 0; |
offroad | 0:80f1104f405a | 27 | break; |
offroad | 0:80f1104f405a | 28 | |
offroad | 0:80f1104f405a | 29 | default: |
offroad | 0:80f1104f405a | 30 | /* store received byte */ |
offroad | 0:80f1104f405a | 31 | self->data[self -> state - 2] = c; |
offroad | 0:80f1104f405a | 32 | ++self->state; |
offroad | 0:80f1104f405a | 33 | |
offroad | 0:80f1104f405a | 34 | if (self->state == NUM_BYTES_IN_FRAME){ |
offroad | 0:80f1104f405a | 35 | /* one complete frame was received. |
offroad | 0:80f1104f405a | 36 | * - Copy the data |
offroad | 0:80f1104f405a | 37 | * - mask out bits 10..15 |
offroad | 0:80f1104f405a | 38 | */ |
offroad | 0:80f1104f405a | 39 | int ix; |
offroad | 0:80f1104f405a | 40 | for (ix = 0; ix < NUM_CHAN; ++ix){ |
offroad | 0:80f1104f405a | 41 | self->out[ix] = ((self->data[2*ix] & 3) << 8) | self->data[2*ix+1]; |
offroad | 0:80f1104f405a | 42 | } |
offroad | 0:80f1104f405a | 43 | |
offroad | 0:80f1104f405a | 44 | /* output data is now valid */ |
offroad | 0:80f1104f405a | 45 | self->valid = true; |
offroad | 0:80f1104f405a | 46 | ++self->frameNum; |
offroad | 0:80f1104f405a | 47 | |
offroad | 0:80f1104f405a | 48 | /* ready for the next frame */ |
offroad | 0:80f1104f405a | 49 | self->state = 0; |
offroad | 0:80f1104f405a | 50 | } /* if frame complete */ |
offroad | 0:80f1104f405a | 51 | } /* switch state */ |
offroad | 0:80f1104f405a | 52 | } |
offroad | 0:80f1104f405a | 53 | |
offroad | 0:80f1104f405a | 54 | void spektRx_runSerial(spektRx_t* self, Serial* s){ |
offroad | 0:80f1104f405a | 55 | while(s -> readable()) |
offroad | 0:80f1104f405a | 56 | spektRx_runChar(self, s -> getc()); |
offroad | 0:80f1104f405a | 57 | } |
offroad | 0:80f1104f405a | 58 | |
offroad | 0:80f1104f405a | 59 | unsigned short* spektRx_getChannelData(spektRx_t* self){ |
offroad | 0:80f1104f405a | 60 | return (unsigned short*) self -> out; |
offroad | 0:80f1104f405a | 61 | } |
offroad | 0:80f1104f405a | 62 | |
offroad | 0:80f1104f405a | 63 | float spektRx_getChannelValue(spektRx_t* self, char ixChan){ |
offroad | 0:80f1104f405a | 64 | return (float)self->out[ixChan] / 512.0f - 1.0f; |
offroad | 0:80f1104f405a | 65 | } |
offroad | 0:80f1104f405a | 66 | |
offroad | 0:80f1104f405a | 67 | long spektRx_getFrameNum(spektRx_t* self){ |
offroad | 0:80f1104f405a | 68 | return self->frameNum; |
offroad | 0:80f1104f405a | 69 | } |
offroad | 0:80f1104f405a | 70 | |
offroad | 0:80f1104f405a | 71 | void spektRx_invalidateFrame(spektRx_t* self){ |
offroad | 0:80f1104f405a | 72 | self->valid = false; |
offroad | 0:80f1104f405a | 73 | } |