rtl_433/src/devices/ht680.c

103 lines
3.4 KiB
C

/** @file
HT680 based Remote control (broadly similar to x1527 protocol).
Copyright (C) 2016 Igor Polovnikov
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
*/
/**
HT680 based Remote control (broadly similar to x1527 protocol).
- short is 850 us gap 260 us pulse
- long is 434 us gap 663 us pulse
*/
#include "decoder.h"
static int ht680_callback(r_device *decoder, bitbuffer_t *bitbuffer)
{
data_t *data;
uint8_t b[5]; // 36 bits
for (int row = 0; row < bitbuffer->num_rows; row++) {
if (bitbuffer->bits_per_row[row] != 41 || // Length of packet is 41 (36+5)
(bitbuffer->bb[row][0] & 0xf8) != 0xa8) // Sync is 10101xxx (5 bits)
continue; // DECODE_ABORT_LENGTH
// remove the 5 sync bits
bitbuffer_extract_bytes(bitbuffer, row, 5, b, 36);
if ((b[1] & 0xf0) != 0xa0 && // A4, A5 always "open" on HT680
(b[2] & 0x0c) != 0x08 && // AD10 always "open" on HT680
(b[3] & 0x30) != 0x20 && // AD13 always "open" on HT680
(b[4] & 0xf0) != 0xa0) // AD16, AD17 always "open" on HT680
continue; // DECODE_ABORT_EARLY
// Tristate coding
char tristate[21];
char *p = tristate;
for (int byte = 0; byte < 5; byte++) {
for (int bit = 7; bit > 0; bit -= 2) {
switch ((b[byte] >> (bit-1)) & 0x03) {
case 0x00: *p++ = '0'; break;
case 0x01: *p++ = 'X'; break; // Invalid code 01
case 0x02: *p++ = 'Z'; break; // Floating state Z is 10
case 0x03: *p++ = '1'; break;
default: *p++ = '?'; break; // Unknown error
}
}
}
// remove last two unused bits
p -= 2;
*p = '\0';
int address = (b[0]<<12) | (b[1]<<4) | b[2] >> 4;
int button1 = (b[3]>>0) & 0x03;
int button2 = (b[3]>>2) & 0x03;
int button3 = (b[3]>>6) & 0x03;
int button4 = (b[2]>>0) & 0x03;
/* clang-format off */
data = data_make(
"model", "", DATA_STRING, "HT680-Remote",
"id", "Address", DATA_FORMAT, "0x%06X", DATA_INT, address,
"button1", "Button 1", DATA_STRING, button1 == 3 ? "PRESSED" : "",
"button2", "Button 2", DATA_STRING, button2 == 3 ? "PRESSED" : "",
"button3", "Button 3", DATA_STRING, button3 == 3 ? "PRESSED" : "",
"button4", "Button 4", DATA_STRING, button4 == 3 ? "PRESSED" : "",
"tristate", "Tristate code", DATA_STRING, tristate,
NULL);
/* clang-format on */
decoder_output_data(decoder, data);
return 1;
}
return 0;
}
static char const *const output_fields[] = {
"model",
"id",
"button1",
"button2",
"button3",
"button4",
"tristate",
NULL,
};
r_device const ht680 = {
.name = "HT680 Remote control",
.modulation = OOK_PULSE_PWM,
.short_width = 200,
.long_width = 600,
.gap_limit = 1200,
.reset_limit = 14000,
.decode_fn = &ht680_callback,
.fields = output_fields,
};