39 void setFrameSize(
uint8_t size)
override { _frameSize = size; }
41 bool begin(uint8_t frameSize)
override {
42 setFrameSize(frameSize);
46 bool begin()
override {
49 dmaChannel = dma_claim_unused_channel(
true);
50 if (dmaChannel < 0)
return false;
51 dma_channel_config cfg = dma_channel_get_default_config(dmaChannel);
52 channel_config_set_transfer_data_size(&cfg, DMA_SIZE_32);
53 channel_config_set_read_increment(&cfg,
false);
54 channel_config_set_write_increment(&cfg,
true);
55 bool dma_config_ok = dma_channel_configure(
56 dmaChannel, &cfg, dmaBuf, &pio0->rxfifo[0], DMA_BUF_SIZE,
false);
57 if (!dma_config_ok)
return false;
58 dma_channel_start(dmaChannel);
60 pinMode(_rxPin, INPUT);
63 uint sm = pio_claim_unused_sm(pio,
true);
64 if (sm == (uint)-1)
return false;
65 uint offset = pio_add_program(pio, (
const pio_program_t*)&ir_rx_program);
66 if (offset == (uint)-1)
return false;
67 pio_sm_config c = pio_get_default_sm_config();
68 sm_config_set_in_pins(&c, _rxPin);
69 sm_config_set_clkdiv(&c, 1.0f);
70 pio_sm_set_consecutive_pindirs(pio, sm, _rxPin, 1,
false);
71 pio_sm_init(pio, sm, offset, &c);
72 pio_sm_set_enabled(pio, sm,
true);
78 while (dmaBufHead < DMA_BUF_SIZE) {
79 uint32_t data = dmaBuf[dmaBufHead++];
80 uint32_t duration = data & 0xFFFFFF;
81 bool level = (data >> 24) & 0x01;
84 _lastEdgeTime = micros();
87 if (dmaBufHead >= DMA_BUF_SIZE) dmaBufHead = 0;
91 uint32_t now = micros();
92 if (!_edgeDurations.
empty() && (now - _lastEdgeTime > _timeoutUs)) {
94 uint8_t buffer[32] = {0};
96 if (_codec.
decodeEdge(0, 0, 0, 0, buffer, _frameSize, frameLen)) {
103 for (
size_t j = 0; j < frameLen - 1; ++j) sum += buffer[j];
104 valid = (sum == buffer[frameLen - 1]);
108 for (
size_t i = 0; i < frameLen; ++i)
112 _edgeDurations.
clear();
123 if (decodeFrame(
buffer, _frameSize)) {
137 return _frameBuffer.
size();
149 static constexpr size_t DMA_BUF_SIZE = 128;
151 volatile size_t dmaBufHead = 0;
153 bool _useChecksum =
false;
157 static const uint16_t ir_rx_program[4] = {
165 bool decodeFrame(uint8_t* buffer,
size_t frameSize) {
168 for (
size_t i = 0; i < _edgeDurations.
size(); ++i) {
169 if (_codec.
decodeEdge(_edgeDurations[i], _edgeLevels[i], 0, 0, buffer,
170 frameSize, frameLen)) {
177 for (
size_t j = 0; j < frameLen - 1; ++j) sum += buffer[j];
178 valid = (sum == buffer[frameLen - 1]);
184 _edgeDurations.
begin() + i + 1);