Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
irRecv.cpp@3:17440cf7ab90, 2016-01-23 (annotated)
- Committer:
 - yuhki50
 - Date:
 - Sat Jan 23 15:09:34 2016 +0000
 - Revision:
 - 3:17440cf7ab90
 - Parent:
 - 0:70c8e56bac45
 - Child:
 - 4:5e46ae042bc7
 
porting
Who changed what in which revision?
| User | Revision | Line number | New contents of line | 
|---|---|---|---|
| yuhki50 | 0:70c8e56bac45 | 1 | #include "IRremote.h" | 
| yuhki50 | 0:70c8e56bac45 | 2 | #include "IRremoteInt.h" | 
| yuhki50 | 0:70c8e56bac45 | 3 | |
| yuhki50 | 0:70c8e56bac45 | 4 | //+============================================================================= | 
| yuhki50 | 0:70c8e56bac45 | 5 | // Decodes the received IR message | 
| yuhki50 | 0:70c8e56bac45 | 6 | // Returns 0 if no data ready, 1 if data ready. | 
| yuhki50 | 0:70c8e56bac45 | 7 | // Results of decoding are stored in results | 
| yuhki50 | 0:70c8e56bac45 | 8 | // | 
| yuhki50 | 0:70c8e56bac45 | 9 | int IRrecv::decode (decode_results *results) | 
| yuhki50 | 0:70c8e56bac45 | 10 | { | 
| yuhki50 | 0:70c8e56bac45 | 11 | results->rawbuf = irparams.rawbuf; | 
| yuhki50 | 0:70c8e56bac45 | 12 | results->rawlen = irparams.rawlen; | 
| yuhki50 | 0:70c8e56bac45 | 13 | |
| yuhki50 | 0:70c8e56bac45 | 14 | results->overflow = irparams.overflow; | 
| yuhki50 | 0:70c8e56bac45 | 15 | |
| yuhki50 | 0:70c8e56bac45 | 16 | if (irparams.rcvstate != STATE_STOP) return false ; | 
| yuhki50 | 0:70c8e56bac45 | 17 | |
| yuhki50 | 0:70c8e56bac45 | 18 | #if DECODE_NEC | 
| yuhki50 | 0:70c8e56bac45 | 19 | DBG_PRINTLN("Attempting NEC decode"); | 
| yuhki50 | 0:70c8e56bac45 | 20 | if (decodeNEC(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 21 | #endif | 
| yuhki50 | 0:70c8e56bac45 | 22 | |
| yuhki50 | 0:70c8e56bac45 | 23 | #if DECODE_SONY | 
| yuhki50 | 0:70c8e56bac45 | 24 | DBG_PRINTLN("Attempting Sony decode"); | 
| yuhki50 | 0:70c8e56bac45 | 25 | if (decodeSony(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 26 | #endif | 
| yuhki50 | 0:70c8e56bac45 | 27 | |
| yuhki50 | 0:70c8e56bac45 | 28 | #if DECODE_SANYO | 
| yuhki50 | 0:70c8e56bac45 | 29 | DBG_PRINTLN("Attempting Sanyo decode"); | 
| yuhki50 | 0:70c8e56bac45 | 30 | if (decodeSanyo(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 31 | #endif | 
| yuhki50 | 0:70c8e56bac45 | 32 | |
| yuhki50 | 0:70c8e56bac45 | 33 | #if DECODE_MITSUBISHI | 
| yuhki50 | 0:70c8e56bac45 | 34 | DBG_PRINTLN("Attempting Mitsubishi decode"); | 
| yuhki50 | 0:70c8e56bac45 | 35 | if (decodeMitsubishi(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 36 | #endif | 
| yuhki50 | 0:70c8e56bac45 | 37 | |
| yuhki50 | 0:70c8e56bac45 | 38 | #if DECODE_RC5 | 
| yuhki50 | 0:70c8e56bac45 | 39 | DBG_PRINTLN("Attempting RC5 decode"); | 
| yuhki50 | 0:70c8e56bac45 | 40 | if (decodeRC5(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 41 | #endif | 
| yuhki50 | 0:70c8e56bac45 | 42 | |
| yuhki50 | 0:70c8e56bac45 | 43 | #if DECODE_RC6 | 
| yuhki50 | 0:70c8e56bac45 | 44 | DBG_PRINTLN("Attempting RC6 decode"); | 
| yuhki50 | 0:70c8e56bac45 | 45 | if (decodeRC6(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 46 | #endif | 
| yuhki50 | 0:70c8e56bac45 | 47 | |
| yuhki50 | 0:70c8e56bac45 | 48 | #if DECODE_PANASONIC | 
| yuhki50 | 0:70c8e56bac45 | 49 | DBG_PRINTLN("Attempting Panasonic decode"); | 
| yuhki50 | 0:70c8e56bac45 | 50 | if (decodePanasonic(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 51 | #endif | 
| yuhki50 | 0:70c8e56bac45 | 52 | |
| yuhki50 | 0:70c8e56bac45 | 53 | #if DECODE_LG | 
| yuhki50 | 0:70c8e56bac45 | 54 | DBG_PRINTLN("Attempting LG decode"); | 
| yuhki50 | 0:70c8e56bac45 | 55 | if (decodeLG(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 56 | #endif | 
| yuhki50 | 0:70c8e56bac45 | 57 | |
| yuhki50 | 0:70c8e56bac45 | 58 | #if DECODE_JVC | 
| yuhki50 | 0:70c8e56bac45 | 59 | DBG_PRINTLN("Attempting JVC decode"); | 
| yuhki50 | 0:70c8e56bac45 | 60 | if (decodeJVC(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 61 | #endif | 
| yuhki50 | 0:70c8e56bac45 | 62 | |
| yuhki50 | 0:70c8e56bac45 | 63 | #if DECODE_SAMSUNG | 
| yuhki50 | 0:70c8e56bac45 | 64 | DBG_PRINTLN("Attempting SAMSUNG decode"); | 
| yuhki50 | 0:70c8e56bac45 | 65 | if (decodeSAMSUNG(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 66 | #endif | 
| yuhki50 | 0:70c8e56bac45 | 67 | |
| yuhki50 | 0:70c8e56bac45 | 68 | #if DECODE_WHYNTER | 
| yuhki50 | 0:70c8e56bac45 | 69 | DBG_PRINTLN("Attempting Whynter decode"); | 
| yuhki50 | 0:70c8e56bac45 | 70 | if (decodeWhynter(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 71 | #endif | 
| yuhki50 | 0:70c8e56bac45 | 72 | |
| yuhki50 | 0:70c8e56bac45 | 73 | #if DECODE_AIWA_RC_T501 | 
| yuhki50 | 0:70c8e56bac45 | 74 | DBG_PRINTLN("Attempting Aiwa RC-T501 decode"); | 
| yuhki50 | 0:70c8e56bac45 | 75 | if (decodeAiwaRCT501(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 76 | #endif | 
| yuhki50 | 0:70c8e56bac45 | 77 | |
| yuhki50 | 0:70c8e56bac45 | 78 | #if DECODE_DENON | 
| yuhki50 | 0:70c8e56bac45 | 79 | DBG_PRINTLN("Attempting Denon decode"); | 
| yuhki50 | 0:70c8e56bac45 | 80 | if (decodeDenon(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 81 | #endif | 
| yuhki50 | 0:70c8e56bac45 | 82 | |
| yuhki50 | 0:70c8e56bac45 | 83 | // decodeHash returns a hash on any input. | 
| yuhki50 | 0:70c8e56bac45 | 84 | // Thus, it needs to be last in the list. | 
| yuhki50 | 0:70c8e56bac45 | 85 | // If you add any decodes, add them before this. | 
| yuhki50 | 0:70c8e56bac45 | 86 | if (decodeHash(results)) return true ; | 
| yuhki50 | 0:70c8e56bac45 | 87 | |
| yuhki50 | 0:70c8e56bac45 | 88 | // Throw away and start over | 
| yuhki50 | 0:70c8e56bac45 | 89 | resume(); | 
| yuhki50 | 0:70c8e56bac45 | 90 | return false; | 
| yuhki50 | 0:70c8e56bac45 | 91 | } | 
| yuhki50 | 0:70c8e56bac45 | 92 | |
| yuhki50 | 0:70c8e56bac45 | 93 | //+============================================================================= | 
| yuhki50 | 3:17440cf7ab90 | 94 | IRrecv::IRrecv (PinName recvpin) : _recvpin(recvpin) | 
| yuhki50 | 0:70c8e56bac45 | 95 | { | 
| yuhki50 | 3:17440cf7ab90 | 96 | _recvpin.mode(PullNone); | 
| yuhki50 | 0:70c8e56bac45 | 97 | } | 
| yuhki50 | 0:70c8e56bac45 | 98 | |
| yuhki50 | 0:70c8e56bac45 | 99 | //+============================================================================= | 
| yuhki50 | 3:17440cf7ab90 | 100 | // enable IR receive | 
| yuhki50 | 0:70c8e56bac45 | 101 | // | 
| yuhki50 | 0:70c8e56bac45 | 102 | void IRrecv::enableIRIn ( ) | 
| yuhki50 | 0:70c8e56bac45 | 103 | { | 
| yuhki50 | 3:17440cf7ab90 | 104 | _ticker.detach(); | 
| yuhki50 | 3:17440cf7ab90 | 105 | _ticker.attach_us(this, &IRrecv::timer_isr, USECPERTICK); | 
| yuhki50 | 0:70c8e56bac45 | 106 | |
| yuhki50 | 0:70c8e56bac45 | 107 | // Initialize state machine variables | 
| yuhki50 | 0:70c8e56bac45 | 108 | irparams.rcvstate = STATE_IDLE; | 
| yuhki50 | 0:70c8e56bac45 | 109 | irparams.rawlen = 0; | 
| yuhki50 | 0:70c8e56bac45 | 110 | } | 
| yuhki50 | 0:70c8e56bac45 | 111 | |
| yuhki50 | 0:70c8e56bac45 | 112 | //+============================================================================= | 
| yuhki50 | 3:17440cf7ab90 | 113 | // disable IR receive | 
| yuhki50 | 0:70c8e56bac45 | 114 | // | 
| yuhki50 | 3:17440cf7ab90 | 115 | void IRrecv::disableIRIn ( ) | 
| yuhki50 | 0:70c8e56bac45 | 116 | { | 
| yuhki50 | 3:17440cf7ab90 | 117 | _ticker.detach(); | 
| yuhki50 | 0:70c8e56bac45 | 118 | } | 
| yuhki50 | 0:70c8e56bac45 | 119 | |
| yuhki50 | 0:70c8e56bac45 | 120 | //+============================================================================= | 
| yuhki50 | 0:70c8e56bac45 | 121 | // Return if receiving new IR signals | 
| yuhki50 | 0:70c8e56bac45 | 122 | // | 
| yuhki50 | 0:70c8e56bac45 | 123 | bool IRrecv::isIdle ( ) | 
| yuhki50 | 0:70c8e56bac45 | 124 | { | 
| yuhki50 | 0:70c8e56bac45 | 125 | return (irparams.rcvstate == STATE_IDLE || irparams.rcvstate == STATE_STOP) ? true : false; | 
| yuhki50 | 0:70c8e56bac45 | 126 | } | 
| yuhki50 | 3:17440cf7ab90 | 127 | |
| yuhki50 | 0:70c8e56bac45 | 128 | //+============================================================================= | 
| yuhki50 | 0:70c8e56bac45 | 129 | // Restart the ISR state machine | 
| yuhki50 | 0:70c8e56bac45 | 130 | // | 
| yuhki50 | 0:70c8e56bac45 | 131 | void IRrecv::resume ( ) | 
| yuhki50 | 0:70c8e56bac45 | 132 | { | 
| yuhki50 | 0:70c8e56bac45 | 133 | irparams.rcvstate = STATE_IDLE; | 
| yuhki50 | 0:70c8e56bac45 | 134 | irparams.rawlen = 0; | 
| yuhki50 | 0:70c8e56bac45 | 135 | } | 
| yuhki50 | 0:70c8e56bac45 | 136 | |
| yuhki50 | 0:70c8e56bac45 | 137 | //+============================================================================= | 
| yuhki50 | 0:70c8e56bac45 | 138 | // hashdecode - decode an arbitrary IR code. | 
| yuhki50 | 0:70c8e56bac45 | 139 | // Instead of decoding using a standard encoding scheme | 
| yuhki50 | 0:70c8e56bac45 | 140 | // (e.g. Sony, NEC, RC5), the code is hashed to a 32-bit value. | 
| yuhki50 | 0:70c8e56bac45 | 141 | // | 
| yuhki50 | 0:70c8e56bac45 | 142 | // The algorithm: look at the sequence of MARK signals, and see if each one | 
| yuhki50 | 0:70c8e56bac45 | 143 | // is shorter (0), the same length (1), or longer (2) than the previous. | 
| yuhki50 | 0:70c8e56bac45 | 144 | // Do the same with the SPACE signals. Hash the resulting sequence of 0's, | 
| yuhki50 | 0:70c8e56bac45 | 145 | // 1's, and 2's to a 32-bit value. This will give a unique value for each | 
| yuhki50 | 0:70c8e56bac45 | 146 | // different code (probably), for most code systems. | 
| yuhki50 | 0:70c8e56bac45 | 147 | // | 
| yuhki50 | 0:70c8e56bac45 | 148 | // http://arcfn.com/2010/01/using-arbitrary-remotes-with-arduino.html | 
| yuhki50 | 0:70c8e56bac45 | 149 | // | 
| yuhki50 | 0:70c8e56bac45 | 150 | // Compare two tick values, returning 0 if newval is shorter, | 
| yuhki50 | 0:70c8e56bac45 | 151 | // 1 if newval is equal, and 2 if newval is longer | 
| yuhki50 | 0:70c8e56bac45 | 152 | // Use a tolerance of 20% | 
| yuhki50 | 0:70c8e56bac45 | 153 | // | 
| yuhki50 | 0:70c8e56bac45 | 154 | int IRrecv::compare (unsigned int oldval, unsigned int newval) | 
| yuhki50 | 0:70c8e56bac45 | 155 | { | 
| yuhki50 | 0:70c8e56bac45 | 156 | if (newval < oldval * .8) return 0 ; | 
| yuhki50 | 0:70c8e56bac45 | 157 | else if (oldval < newval * .8) return 2 ; | 
| yuhki50 | 0:70c8e56bac45 | 158 | else return 1 ; | 
| yuhki50 | 0:70c8e56bac45 | 159 | } | 
| yuhki50 | 0:70c8e56bac45 | 160 | |
| yuhki50 | 0:70c8e56bac45 | 161 | //+============================================================================= | 
| yuhki50 | 0:70c8e56bac45 | 162 | // Use FNV hash algorithm: http://isthe.com/chongo/tech/comp/fnv/#FNV-param | 
| yuhki50 | 0:70c8e56bac45 | 163 | // Converts the raw code values into a 32-bit hash code. | 
| yuhki50 | 0:70c8e56bac45 | 164 | // Hopefully this code is unique for each button. | 
| yuhki50 | 0:70c8e56bac45 | 165 | // This isn't a "real" decoding, just an arbitrary value. | 
| yuhki50 | 0:70c8e56bac45 | 166 | // | 
| yuhki50 | 0:70c8e56bac45 | 167 | #define FNV_PRIME_32 16777619 | 
| yuhki50 | 0:70c8e56bac45 | 168 | #define FNV_BASIS_32 2166136261 | 
| yuhki50 | 0:70c8e56bac45 | 169 | |
| yuhki50 | 0:70c8e56bac45 | 170 | long IRrecv::decodeHash (decode_results *results) | 
| yuhki50 | 0:70c8e56bac45 | 171 | { | 
| yuhki50 | 0:70c8e56bac45 | 172 | long hash = FNV_BASIS_32; | 
| yuhki50 | 0:70c8e56bac45 | 173 | |
| yuhki50 | 0:70c8e56bac45 | 174 | // Require at least 6 samples to prevent triggering on noise | 
| yuhki50 | 0:70c8e56bac45 | 175 | if (results->rawlen < 6) return false ; | 
| yuhki50 | 0:70c8e56bac45 | 176 | |
| yuhki50 | 0:70c8e56bac45 | 177 | for (int i = 1; (i + 2) < results->rawlen; i++) { | 
| yuhki50 | 0:70c8e56bac45 | 178 | int value = compare(results->rawbuf[i], results->rawbuf[i+2]); | 
| yuhki50 | 0:70c8e56bac45 | 179 | // Add value into the hash | 
| yuhki50 | 0:70c8e56bac45 | 180 | hash = (hash * FNV_PRIME_32) ^ value; | 
| yuhki50 | 0:70c8e56bac45 | 181 | } | 
| yuhki50 | 0:70c8e56bac45 | 182 | |
| yuhki50 | 0:70c8e56bac45 | 183 | results->value = hash; | 
| yuhki50 | 0:70c8e56bac45 | 184 | results->bits = 32; | 
| yuhki50 | 0:70c8e56bac45 | 185 | results->decode_type = UNKNOWN; | 
| yuhki50 | 0:70c8e56bac45 | 186 | |
| yuhki50 | 0:70c8e56bac45 | 187 | return true; | 
| yuhki50 | 0:70c8e56bac45 | 188 | } |