flipperzero-firmware/applications/lfrfid/helpers/decoder-indala.cpp
SG 6926cf8b7e
[FL-1449] Indala reading and writing (#616)
* Rfid: indala 40134 validation and decoding
* Rfid: show indala info
* Rfid: decoder to output comparator signal on gpio pins
* Rfid: working indala 40134 decoder
* HAL: added function to change rfid timer parameters on the fly
* RFID: Indala reading, card detection, card verification
* Rfid: indala writing
2021-08-02 01:11:18 +03:00

76 lines
1.8 KiB
C++

#include "decoder-indala.h"
#include <api-hal.h>
constexpr uint32_t clocks_in_us = 64;
constexpr uint32_t us_per_bit = 255;
bool DecoderIndala::read(uint8_t* data, uint8_t data_size) {
bool result = false;
if(ready) {
result = true;
if(cursed_data_valid) {
indala.decode(
reinterpret_cast<const uint8_t*>(&cursed_raw_data),
sizeof(uint64_t),
data,
data_size);
} else {
indala.decode(
reinterpret_cast<const uint8_t*>(&raw_data), sizeof(uint64_t), data, data_size);
}
reset_state();
}
return result;
}
void DecoderIndala::process_front(bool polarity, uint32_t time) {
if(ready) return;
process_internal(polarity, time, &raw_data);
if(ready) return;
if(polarity) {
time = time + 110;
} else {
time = time - 110;
}
process_internal(!polarity, time, &cursed_raw_data);
if(ready) {
cursed_data_valid = true;
}
}
void DecoderIndala::process_internal(bool polarity, uint32_t time, uint64_t* data) {
time /= clocks_in_us;
time += (us_per_bit / 2);
uint32_t bit_count = (time / us_per_bit);
if(bit_count < 64) {
for(uint32_t i = 0; i < bit_count; i++) {
*data = (*data << 1) | polarity;
if((*data >> 32) == 0xa0000000ULL) {
if(indala.can_be_decoded(
reinterpret_cast<const uint8_t*>(data), sizeof(uint64_t))) {
ready = true;
break;
}
}
}
}
}
DecoderIndala::DecoderIndala() {
reset_state();
}
void DecoderIndala::reset_state() {
raw_data = 0;
cursed_raw_data = 0;
ready = false;
cursed_data_valid = false;
}