| 165 | } |
| 166 | |
| 167 | bool IRrecv::decodeDenon() { |
| 168 | |
| 169 | // we have no start bit, so check for the exact amount of data bits |
| 170 | // Check we have the right amount of data (32). The + 2 is for initial gap + stop bit mark |
| 171 | if (decodedIRData.rawlen != (2 * DENON_BITS) + 2) { |
| 172 | DEBUG_PRINT(F("Denon: Data length=")); |
| 173 | DEBUG_PRINT(decodedIRData.rawlen); |
| 174 | DEBUG_PRINTLN(F(" is not 32")); |
| 175 | return false; |
| 176 | } |
| 177 | |
| 178 | // Check for first mark, which is no AGC or start bit. This prevents Sony15 from being decoded as Denon. |
| 179 | // matchMark is too sensitive! |
| 180 | if (irparams.rawbuf[1] >= ((2 * DENON_HEADER_MARK) / MICROS_PER_TICK)) { |
| 181 | DEBUG_PRINTLN(F("Denon: First mark length is wrong")); |
| 182 | return false; |
| 183 | } |
| 184 | |
| 185 | // Try to decode as Denon protocol |
| 186 | decodePulseDistanceWidthData_P(&DenonProtocolConstants, DENON_BITS, 1); |
| 187 | |
| 188 | // Success |
| 189 | decodedIRData.address = decodedIRData.decodedRawData & 0x1F; |
| 190 | decodedIRData.command = decodedIRData.decodedRawData >> DENON_ADDRESS_BITS; |
| 191 | uint8_t tFrameBits = (decodedIRData.command >> 8) & 0x03; |
| 192 | decodedIRData.command &= 0xFF; |
| 193 | |
| 194 | // Check for (auto) repeat |
| 195 | if (decodedIRData.initialGapTicks < ((DENON_AUTO_REPEAT_DISTANCE + (DENON_AUTO_REPEAT_DISTANCE / 4)) / MICROS_PER_TICK)) { |
| 196 | decodedIRData.flags |= IRDATA_FLAGS_IS_AUTO_REPEAT; |
| 197 | |
| 198 | repeatCount++; |
| 199 | /* |
| 200 | * 1. repeat is inverted autorepeat -> IRDATA_FLAGS_IS_AUTO_REPEAT |
| 201 | * 2. repeat is normal autorepeat (end) or 1. normal repeat -> IRDATA_FLAGS_IS_AUTO_REPEAT |
| 202 | * 3. repeat is inverted autorepeat of the 1. repeat -> IRDATA_FLAGS_IS_REPEAT (not the correct frame, but this enables easy counting of repeats) |
| 203 | * 4. repeat is normal autorepeat (end) or 2. normal repeat -> IRDATA_FLAGS_IS_AUTO_REPEAT |
| 204 | * 5. repeat is inverted autorepeat of the 2. repeat -> IRDATA_FLAGS_IS_REPEAT (not the correct frame, but this enables easy counting of repeats) |
| 205 | * 6. repeat is normal autorepeat (end) or 3. normal repeat -> IRDATA_FLAGS_IS_AUTO_REPEAT |
| 206 | */ |
| 207 | |
| 208 | if (repeatCount & 0x01) { |
| 209 | /* |
| 210 | * Here we are in an inverted auto repeated frame where the command and frame bits are inverted |
| 211 | */ |
| 212 | DEBUG_PRINTLN(F("Denon: Inverted frame")); |
| 213 | |
| 214 | if (repeatCount > 1) { // skip first auto repeat |
| 215 | decodedIRData.flags = IRDATA_FLAGS_IS_REPEAT; |
| 216 | } |
| 217 | // Check parity of consecutive received commands. There is no parity in one data set. |
| 218 | if ((uint8_t) lastDecodedCommand != (uint8_t)(~decodedIRData.command)) { |
| 219 | decodedIRData.flags |= IRDATA_FLAGS_PARITY_FAILED; |
| 220 | |
| 221 | DEBUG_PRINT(F("Denon: Parity check of inverted with non inverted frame failed. Last command=")); |
| 222 | DEBUG_PRINT((uint8_t )lastDecodedCommand, HEX); |
| 223 | DEBUG_PRINT(F(" current=")); |
| 224 | DEBUG_PRINTLN((uint8_t )~decodedIRData.command, HEX); |
nothing calls this directly
no outgoing calls
no test coverage detected