Browse Source

Improve NEC reading code

Now the NEC reading code is more cautious about what it accepts, more
readily throwing away input if anything odd is read.  It also, and this
is the big one, sends an event as soon as it's read all 32 bits, so I
can actually read short button presses now(!).  I'm not aware of any
major reliability problems left, so I'm leaving the translator by the TV
for now.
Clara Hobbs 7 years ago
parent
commit
d102f5f00f
1 changed files with 35 additions and 22 deletions
  1. 35
    22
      src/main.c

+ 35
- 22
src/main.c View File

@@ -68,7 +68,7 @@
68 68
  */
69 69
 #define NEC_START_PULSE 45
70 70
 #define NEC_END_PULSE 405
71
-#define NEC_RPT_CMD_PULSE 959
71
+#define NEC_RPT_CMD_PULSE 962
72 72
 #define NEC_ZERO_PULSE 6
73 73
 #define NEC_ONE_PULSE 17
74 74
 #define NEC_COMMA_PULSE 23
@@ -105,7 +105,7 @@ static const GPTConfig gpt4cfg = {
105 105
 
106 106
 
107 107
 /*
108
- * Variables for holding the most recently read information from icuwidthcb
108
+ * Variables for holding the most recently read information from nec_icuwidthcb
109 109
  */
110 110
 static uint8_t nec_addr, nec_data;
111 111
 static bool nec_repeat = false;
@@ -113,36 +113,49 @@ static bool nec_repeat = false;
113 113
 /*
114 114
  * ICU pulse width callback for reading NEC remote control frames
115 115
  */
116
-static void icuwidthcb(ICUDriver *icup)
116
+static void nec_icuwidthcb(ICUDriver *icup)
117 117
 {
118 118
     static int32_t index = -1;
119
-    static bool START_OCCURED = false;
119
+    static bool start_occured = false;
120 120
     static uint32_t tmp;
121 121
 
122 122
     icucnt_t cnt = icuGetWidthX(icup);
123 123
     if (CLOSE_TO(cnt, NEC_START_PULSE, NEC_DELTA)) {
124 124
         index = 0;
125
-        START_OCCURED = true;
125
+        start_occured = true;
126 126
     } else if (CLOSE_TO(cnt, NEC_ONE_PULSE, NEC_DELTA)) {
127
-        tmp |= 1 << (31 - index);
128
-        index++;
127
+        if (index > -1) {
128
+            tmp |= 1 << (31 - index);
129
+            index++;
130
+        }
129 131
     } else if (CLOSE_TO(cnt, NEC_ZERO_PULSE, NEC_DELTA)) {
130
-        tmp &= ~(1 << (31 - index));
131
-        index++;
132
-    } else if (CLOSE_TO(cnt, NEC_END_PULSE, 4*NEC_DELTA)) {
133
-        if ((START_OCCURED) && (index == 32)) {
134
-            nec_addr = (tmp >> 24) & 0xFF;
135
-            nec_data = (tmp >> 8) & 0xFF;
136
-        } else {
137
-            nec_addr = 0;
138
-            nec_data = 0;
132
+        if (index > -1) {
133
+            tmp &= ~(1 << (31 - index));
134
+            index++;
139 135
         }
136
+    } else if (CLOSE_TO(cnt, NEC_END_PULSE, 4*NEC_DELTA)) {
137
+        /* Nothing to do here */
138
+    } else if (CLOSE_TO(cnt, NEC_RPT_CMD_PULSE, 9*NEC_DELTA)) {
139
+        /* Nothing to do here */
140
+    } else if (CLOSE_TO(cnt, NEC_COMMA_PULSE, NEC_DELTA)) {
141
+        nec_repeat = true;
142
+        chEvtBroadcastFlags(&IR_receiver, 0);
143
+    } else {
144
+        /* When an unknown symbol is seen, forget what we've read */
145
+        nec_addr = 0;
146
+        nec_data = 0;
140 147
         nec_repeat = false;
141
-        START_OCCURED = false;
148
+        start_occured = false;
149
+        index = -1;
150
+    }
151
+
152
+    /* If we've read a whole message, send it on */
153
+    if (start_occured && index == 32) {
154
+        nec_addr = (tmp >> 24) & 0xFF;
155
+        nec_data = (tmp >> 8) & 0xFF;
156
+        nec_repeat = false;
157
+        start_occured = false;
142 158
         index = -1;
143
-    } else if (CLOSE_TO(cnt, NEC_RPT_CMD_PULSE, NEC_DELTA)) {
144
-        nec_repeat = true;
145
-    } else if (CLOSE_TO(cnt, NEC_COMMA_PULSE, NEC_DELTA)) {
146 159
         chEvtBroadcastFlags(&IR_receiver, 0);
147 160
     }
148 161
 }
@@ -151,7 +164,7 @@ static void icuwidthcb(ICUDriver *icup)
151 164
 static ICUConfig icucfg = {
152 165
     ICU_INPUT_ACTIVE_HIGH,
153 166
     10000,            /* 10kHz ICU clock frequency. */
154
-    icuwidthcb,
167
+    nec_icuwidthcb,
155 168
     NULL,
156 169
     NULL,
157 170
     ICU_CHANNEL_1,
@@ -236,10 +249,10 @@ int main(void)
236 249
     /* Send a continuous stream of power off signals to the TV */
237 250
     while (true) {
238 251
         if (nec_addr == 0x80 && nec_data == 0x18) {
252
+            palClearPad(GPIOC, GPIOC_LED);
239 253
             if (chEvtWaitAnyTimeout(ALL_EVENTS, MS2ST(200))) {
240 254
                 continue;
241 255
             }
242
-            palClearPad(GPIOC, GPIOC_LED);
243 256
             for (int i = 0; i < 3; i++) {
244 257
                 rc5_frame(false, 0x00, 0x0C);
245 258
                 chThdSleepMilliseconds(90);

Loading…
Cancel
Save