ir_NEC_test.cpp 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331
  1. // Copyright 2017 David Conran
  2. #include "IRsend.h"
  3. #include "IRsend_test.h"
  4. #include "gtest/gtest.h"
  5. // Tests for sendNEC().
  6. // Test sending typical data only.
  7. TEST(TestSendNEC, SendDataOnly) {
  8. IRsendTest irsend(4);
  9. irsend.begin();
  10. irsend.sendNEC(0);
  11. EXPECT_EQ(
  12. "m8960s4480m560s560m560s560m560s560m560s560m560s560m560s560m560s560"
  13. "m560s560m560s560m560s560m560s560m560s560m560s560m560s560m560s560"
  14. "m560s560m560s560m560s560m560s560m560s560m560s560m560s560m560s560"
  15. "m560s560m560s560m560s560m560s560m560s560m560s560m560s560m560s560"
  16. "m560s560m560s58240",
  17. irsend.outputStr());
  18. irsend.sendNEC(0xAA00FF55);
  19. EXPECT_EQ(
  20. "m8960s4480m560s1680m560s560m560s1680m560s560m560s1680m560s560"
  21. "m560s1680m560s560m560s560m560s560m560s560m560s560m560s560m560s560"
  22. "m560s560m560s560m560s1680m560s1680m560s1680m560s1680m560s1680"
  23. "m560s1680m560s1680m560s1680m560s560m560s1680m560s560m560s1680"
  24. "m560s560m560s1680m560s560m560s1680m560s40320",
  25. irsend.outputStr());
  26. }
  27. // Test sending different bit lengths.
  28. TEST(TestSendNEC, SendSmallData) {
  29. IRsendTest irsend(4);
  30. irsend.begin();
  31. irsend.sendNEC(0xA, 4); // Send only 4 data bits.
  32. EXPECT_EQ("m8960s4480m560s1680m560s560m560s1680m560s560m560s87360",
  33. irsend.outputStr());
  34. irsend.sendNEC(0, 8); // Send only 8 data bits.
  35. EXPECT_EQ(
  36. "m8960s4480m560s560m560s560m560s560m560s560m560s560m560s560m560s560"
  37. "m560s560m560s85120",
  38. irsend.outputStr());
  39. irsend.sendNEC(0x1234567890ABCDEF, 64); // Send 64 data bits.
  40. EXPECT_EQ(
  41. "m8960s4480m560s560m560s560m560s560m560s1680m560s560m560s560"
  42. "m560s1680m560s560m560s560m560s560m560s1680m560s1680m560s560"
  43. "m560s1680m560s560m560s560m560s560m560s1680m560s560m560s1680"
  44. "m560s560m560s1680m560s1680m560s560m560s560m560s1680m560s1680"
  45. "m560s1680m560s1680m560s560m560s560m560s560m560s1680m560s560"
  46. "m560s560m560s1680m560s560m560s560m560s560m560s560m560s1680m560s560"
  47. "m560s1680m560s560m560s1680m560s560m560s1680m560s1680m560s1680"
  48. "m560s1680m560s560m560s560m560s1680m560s1680m560s560m560s1680"
  49. "m560s1680m560s1680m560s1680m560s560m560s1680m560s1680m560s1680"
  50. "m560s1680m560s22400",
  51. irsend.outputStr());
  52. }
  53. // Test sending with repeats.
  54. TEST(TestSendNEC, SendWithRepeats) {
  55. IRsendTest irsend(4);
  56. irsend.begin();
  57. irsend.sendNEC(0, 8, 0); // Send a command with 0 repeats.
  58. EXPECT_EQ(
  59. "m8960s4480m560s560m560s560m560s560m560s560m560s560m560s560m560s560"
  60. "m560s560m560s85120",
  61. irsend.outputStr());
  62. irsend.sendNEC(0xAA, 8, 1); // Send a command with 1 repeat.
  63. EXPECT_EQ(
  64. "m8960s4480m560s1680m560s560m560s1680m560s560m560s1680m560s560"
  65. "m560s1680m560s560m560s80640"
  66. "m8960s2240m560s96320",
  67. irsend.outputStr());
  68. irsend.sendNEC(0xAA, 8, 3); // Send a command with 3 repeats.
  69. EXPECT_EQ(
  70. "m8960s4480m560s1680m560s560m560s1680m560s560m560s1680m560s560"
  71. "m560s1680m560s560m560s80640"
  72. "m8960s2240m560s96320"
  73. "m8960s2240m560s96320"
  74. "m8960s2240m560s96320",
  75. irsend.outputStr());
  76. }
  77. // Tests for encodeNEC().
  78. TEST(TestEncodeNEC, NormalNECEncoding) {
  79. IRsendTest irsend(4);
  80. EXPECT_EQ(0x807F40BF, irsend.encodeNEC(1, 2));
  81. EXPECT_EQ(0x9A656897, irsend.encodeNEC(0x59, 0x16));
  82. }
  83. TEST(TestEncodeNEC, ExtendedNECEncoding) {
  84. IRsendTest irsend(4);
  85. EXPECT_EQ(0x9A806897, irsend.encodeNEC(0x159, 0x16));
  86. }
  87. TEST(TestEncodeNEC, CommandTrimmedTo8Bits) {
  88. IRsendTest irsend(4);
  89. EXPECT_EQ(irsend.encodeNEC(0x1, 0x2), irsend.encodeNEC(0x1, 0xF02));
  90. EXPECT_EQ(irsend.encodeNEC(0xFFF0, 0x2), irsend.encodeNEC(0xFFF0, 0xF02));
  91. }
  92. // Tests for decodeNEC().
  93. // Decode normal NEC messages.
  94. TEST(TestDecodeNEC, NormalNECDecodeWithStrict) {
  95. IRsendTest irsend(4);
  96. IRrecv irrecv(4);
  97. irsend.begin();
  98. // Synthesised Normal NEC message.
  99. irsend.reset();
  100. irsend.sendNEC(irsend.encodeNEC(0x1, 0x2));
  101. irsend.makeDecodeResult();
  102. EXPECT_TRUE(irrecv.decodeNEC(&irsend.capture));
  103. EXPECT_EQ(NEC, irsend.capture.decode_type);
  104. EXPECT_EQ(kNECBits, irsend.capture.bits);
  105. EXPECT_EQ(0x807F40BF, irsend.capture.value);
  106. EXPECT_EQ(0x1, irsend.capture.address);
  107. EXPECT_EQ(0x2, irsend.capture.command);
  108. // Real-life Extended NEC code from an actual capture/decode.
  109. irsend.reset();
  110. irsend.sendNEC(0xC1A28877);
  111. irsend.makeDecodeResult();
  112. EXPECT_TRUE(irrecv.decodeNEC(&irsend.capture));
  113. EXPECT_EQ(NEC, irsend.capture.decode_type);
  114. EXPECT_EQ(kNECBits, irsend.capture.bits);
  115. EXPECT_EQ(0xC1A28877, irsend.capture.value);
  116. EXPECT_EQ(0x4583, irsend.capture.address);
  117. EXPECT_EQ(0x11, irsend.capture.command);
  118. // Test strict decoding rejects a NEC-like message.
  119. irsend.reset();
  120. irsend.sendNEC(0x0);
  121. irsend.makeDecodeResult();
  122. EXPECT_FALSE(irrecv.decodeNEC(&irsend.capture));
  123. // Synthesised Normal NEC message with a repeat.
  124. irsend.reset();
  125. irsend.sendNEC(irsend.encodeNEC(0x1, 0x2), 32, 1);
  126. irsend.makeDecodeResult();
  127. EXPECT_TRUE(irrecv.decodeNEC(&irsend.capture));
  128. EXPECT_EQ(NEC, irsend.capture.decode_type);
  129. EXPECT_EQ(kNECBits, irsend.capture.bits);
  130. EXPECT_EQ(0x807F40BF, irsend.capture.value);
  131. EXPECT_EQ(0x1, irsend.capture.address);
  132. EXPECT_EQ(0x2, irsend.capture.command);
  133. }
  134. // NEC-like messages without strict mode.
  135. TEST(TestDecodeNEC, NormalNECDecodeWithoutStrict) {
  136. IRsendTest irsend(4);
  137. IRrecv irrecv(4);
  138. irsend.begin();
  139. irsend.reset();
  140. irsend.sendNEC(0x0);
  141. irsend.makeDecodeResult();
  142. EXPECT_TRUE(irrecv.decodeNEC(&irsend.capture, 32, false));
  143. EXPECT_EQ(NEC, irsend.capture.decode_type);
  144. EXPECT_EQ(kNECBits, irsend.capture.bits);
  145. EXPECT_EQ(0, irsend.capture.value);
  146. EXPECT_EQ(0, irsend.capture.address);
  147. EXPECT_EQ(0, irsend.capture.command);
  148. irsend.reset();
  149. irsend.sendNEC(0x12345678);
  150. irsend.makeDecodeResult();
  151. EXPECT_TRUE(irrecv.decodeNEC(&irsend.capture, 32, false));
  152. EXPECT_EQ(NEC, irsend.capture.decode_type);
  153. EXPECT_EQ(kNECBits, irsend.capture.bits);
  154. EXPECT_EQ(0x12345678, irsend.capture.value);
  155. EXPECT_EQ(0x2C48, irsend.capture.address);
  156. EXPECT_EQ(0, irsend.capture.command);
  157. }
  158. // Short NEC-like messages (without strict naturally)
  159. TEST(TestDecodeNEC, ShortNECDecodeWithoutStrict) {
  160. IRsendTest irsend(4);
  161. IRrecv irrecv(4);
  162. irsend.begin();
  163. irsend.reset();
  164. irsend.sendNEC(0x0, 16);
  165. irsend.makeDecodeResult();
  166. EXPECT_TRUE(irrecv.decodeNEC(&irsend.capture, 16, false));
  167. EXPECT_EQ(NEC, irsend.capture.decode_type);
  168. EXPECT_EQ(16, irsend.capture.bits);
  169. EXPECT_EQ(0, irsend.capture.value);
  170. EXPECT_EQ(0, irsend.capture.address);
  171. EXPECT_EQ(0, irsend.capture.command);
  172. // Expecting less than what was sent is not valid.
  173. irsend.reset();
  174. irsend.sendNEC(0x0, 32);
  175. irsend.makeDecodeResult();
  176. EXPECT_FALSE(irrecv.decodeNEC(&irsend.capture, 16, false));
  177. // Send 16 bits of data, but fail because we are expecting 17.
  178. irsend.reset();
  179. irsend.sendNEC(0x0, 16);
  180. irsend.makeDecodeResult();
  181. EXPECT_FALSE(irrecv.decodeNEC(&irsend.capture, 17, false));
  182. }
  183. // Longer NEC-like messages (without strict naturally)
  184. TEST(TestDecodeNEC, LongerNECDecodeWithoutStrict) {
  185. IRsendTest irsend(4);
  186. IRrecv irrecv(4);
  187. irsend.begin();
  188. irsend.reset();
  189. irsend.sendNEC(0x1234567890ABCDEF, 64);
  190. irsend.makeDecodeResult();
  191. EXPECT_TRUE(irrecv.decodeNEC(&irsend.capture, 64, false));
  192. EXPECT_EQ(NEC, irsend.capture.decode_type);
  193. EXPECT_EQ(64, irsend.capture.bits);
  194. EXPECT_EQ(0x1234567890ABCDEF, irsend.capture.value);
  195. EXPECT_EQ(0xD509, irsend.capture.address);
  196. EXPECT_EQ(0, irsend.capture.command);
  197. // Send 63 bits of data, but fail because we are expecting 64.
  198. irsend.reset();
  199. irsend.sendNEC(0x0, 63);
  200. irsend.makeDecodeResult();
  201. EXPECT_FALSE(irrecv.decodeNEC(&irsend.capture, 64, false));
  202. }
  203. // Incorrect decoding reported in Issue #243
  204. // Incorrect handling of decodes when there is no gap recorded at
  205. // the end of a command when using the interrupt code. sendRaw() best emulates
  206. // this for unit testing purposes. sendGC() and sendXXX() will add the trailing
  207. // gap. Users won't see this in normal use.
  208. TEST(TestDecodeNEC, NoTrailingGap_Issue243) {
  209. IRsendTest irsend(4);
  210. IRrecv irrecv(4);
  211. irsend.begin();
  212. irsend.reset();
  213. uint16_t rawData[67] = {
  214. 9000, 4500, 650, 550, 650, 1650, 600, 550, 650, 550, 600, 1650,
  215. 650, 550, 600, 1650, 650, 1650, 650, 1650, 600, 550, 650, 1650,
  216. 650, 1650, 650, 550, 600, 1650, 650, 1650, 650, 550, 650, 550,
  217. 650, 1650, 650, 550, 650, 550, 650, 550, 600, 550, 650, 550,
  218. 650, 550, 650, 1650, 600, 550, 650, 1650, 650, 1650, 650, 1650,
  219. 650, 1650, 650, 1650, 650, 1650, 600};
  220. irsend.sendRaw(rawData, 67, 38);
  221. irsend.makeDecodeResult();
  222. EXPECT_TRUE(irrecv.decodeNEC(&irsend.capture));
  223. EXPECT_EQ(NEC, irsend.capture.decode_type);
  224. EXPECT_EQ(kNECBits, irsend.capture.bits);
  225. EXPECT_EQ(0x4BB640BF, irsend.capture.value);
  226. EXPECT_EQ(0x6DD2, irsend.capture.address);
  227. EXPECT_EQ(0x2, irsend.capture.command);
  228. irsend.reset();
  229. irsend.sendRaw(rawData, 67, 38);
  230. irsend.makeDecodeResult();
  231. ASSERT_TRUE(irrecv.decode(&irsend.capture));
  232. EXPECT_EQ(NEC, irsend.capture.decode_type);
  233. EXPECT_EQ(kNECBits, irsend.capture.bits);
  234. EXPECT_EQ(0x4BB640BF, irsend.capture.value);
  235. // Add a zero length space to the message to test how it handles that as
  236. // an end of command gap.
  237. irsend.addGap(0);
  238. irsend.makeDecodeResult();
  239. ASSERT_TRUE(irrecv.decode(&irsend.capture));
  240. EXPECT_EQ(NEC, irsend.capture.decode_type);
  241. EXPECT_EQ(kNECBits, irsend.capture.bits);
  242. EXPECT_EQ(0x4BB640BF, irsend.capture.value);
  243. }
  244. // Inconsistent decoding for unknown in Issue #264
  245. // Reported issues decoding an Apple Remote. Apple doesn't appear to respect
  246. // or use the command structure/checks in the NEC protocol.
  247. TEST(TestDecodeNEC, NonStrictNECDecode_Issue264) {
  248. IRsendTest irsend(4);
  249. IRrecv irrecv(4);
  250. irsend.begin();
  251. irsend.reset();
  252. // Slightly modified example than reported due to poor timings that are too
  253. // far out of spec.
  254. uint16_t rawData[67] = {
  255. 9150, 4650, 550, 600, 550, 1800, 600, 1750, 600, 1800, 550, 600,
  256. 550, 1800, 550, 1750, 600, 1750, 600, 1750, 600, 1750, 600, 1700,
  257. 600, 600, 600, 600, 550, 600, 600, 600, 600, 1750, 600, 1750,
  258. 600, 600, 550, 1800, 600, 600, 600, 600, 600, 600, 500, 600,
  259. 600, 600, 600, 600, 600, 1750, 600, 600, 600, 550, 600, 600,
  260. 600, 600, 600, 600, 600, 550, 600};
  261. irsend.sendRaw(rawData, 67, 38);
  262. irsend.makeDecodeResult();
  263. EXPECT_FALSE(irrecv.decodeNEC(&irsend.capture)); // Not strictly NEC
  264. EXPECT_TRUE(irrecv.decodeNEC(&irsend.capture, kNECBits, false));
  265. EXPECT_EQ(0x77E1A040, irsend.capture.value);
  266. // Do it all again, but with a normal decode.
  267. irsend.reset();
  268. irsend.sendRaw(rawData, 67, 38);
  269. irsend.makeDecodeResult();
  270. ASSERT_TRUE(irrecv.decode(&irsend.capture));
  271. EXPECT_EQ(NEC_LIKE, irsend.capture.decode_type);
  272. EXPECT_EQ(kNECBits, irsend.capture.bits);
  273. EXPECT_EQ(0x77E1A040, irsend.capture.value);
  274. }
  275. TEST(TestDecodeNEC, AutoReceiveCalibration) {
  276. IRsendTest irsend(4);
  277. IRrecv irrecv(4);
  278. irsend.begin();
  279. irsend.reset();
  280. // Data from Issue #264, for a remote that is slightly off spec.
  281. // Should be matched as a NEC-like message however without self-calibrating
  282. // the timings of the short spaces is out.
  283. uint16_t rawData[67] = {
  284. 9150, 4600, 650, 600, 650, 1650, 650, 1700, 650, 1750, 650, 600,
  285. 650, 1700, 650, 1750, 650, 1750, 650, 1700, 650, 1700, 650, 1700,
  286. 650, 600, 650, 600, 650, 600, 600, 600, 650, 1750, 650, 1750,
  287. 650, 600, 650, 1700, 600, 600, 700, 550, 650, 550, 650, 600,
  288. 650, 600, 650, 600, 650, 1750, 600, 600, 650, 600, 650, 550,
  289. 650, 600, 650, 600, 650, 600, 600};
  290. irsend.sendRaw(rawData, 67, 38);
  291. irsend.makeDecodeResult();
  292. EXPECT_TRUE(irrecv.decodeNEC(&irsend.capture, kNECBits, false));
  293. EXPECT_EQ(NEC, irsend.capture.decode_type);
  294. EXPECT_EQ(kNECBits, irsend.capture.bits);
  295. EXPECT_EQ(0x77E1A040, irsend.capture.value);
  296. }