kopia lustrzana https://github.com/weetmuts/wmbusmeters
Simulation file and hex on command line now auto-removes any valid dll-crcs found.
rodzic
02e84048f0
commit
f7cb6ce2ee
8
CHANGES
8
CHANGES
|
@ -1,4 +1,12 @@
|
||||||
|
|
||||||
|
Now any DLL crcs (frame A or B) are removed automatically
|
||||||
|
when telegrams are read from a simulation_... file or
|
||||||
|
passed as hex on the command line. If the DLL crc do not
|
||||||
|
check out (usually because they are not there), then the
|
||||||
|
telegram is kept as is. If the crcs are broken because
|
||||||
|
of a bad data, then the telegram will be passed on as is,
|
||||||
|
probably causing a bad parse later on.
|
||||||
|
|
||||||
Added multical602 heat meter.
|
Added multical602 heat meter.
|
||||||
|
|
||||||
Version 1.5.0: 2021-11-06
|
Version 1.5.0: 2021-11-06
|
||||||
|
|
|
@ -303,6 +303,7 @@ These telegrams are expected to have the data link layer crc bytes removed alrea
|
||||||
|
|
||||||
`simulation_abc.txt`, to read telegrams from the file (the file must have a name beginning with simulation_....)
|
`simulation_abc.txt`, to read telegrams from the file (the file must have a name beginning with simulation_....)
|
||||||
expecting the same format that is the output from `--logtelegrams`. This format also supports replay with timing.
|
expecting the same format that is the output from `--logtelegrams`. This format also supports replay with timing.
|
||||||
|
The telegrams are allowed to have valid dll crcs, which will be automatically stripped.
|
||||||
|
|
||||||
As meter quadruples you specify:
|
As meter quadruples you specify:
|
||||||
|
|
||||||
|
@ -604,8 +605,11 @@ echo 234433300602010014007a8e0000002f2f0efd3a1147000000008e40fd3a341200000000 |
|
||||||
|
|
||||||
or read hex data from a a file, `wmbusmeters myfile.txt:hex`
|
or read hex data from a a file, `wmbusmeters myfile.txt:hex`
|
||||||
|
|
||||||
Any non-hex characters are ignored when using the suffix `:hex`. The hex string must be proper
|
Any non-hex characters are ignored when using the suffix `:hex`. However when the hex string is
|
||||||
with no spaces nor bad characters, when supplied on the command line.
|
supplied on the command line it must be a proper hex string with no spaces.
|
||||||
|
|
||||||
|
When a telegram is supplied on the command line, then any valid dll crcs will be automatically removed,
|
||||||
|
like when the telegram is suppled in a simulation file.
|
||||||
|
|
||||||
# Additional tools
|
# Additional tools
|
||||||
|
|
||||||
|
|
|
@ -1,3 +1,3 @@
|
||||||
# This telegram is not really broken, but the current dvparser fails, in particular the end triggers a varlen with
|
# The last byte C4 has been removed. This means that the dll crcs will not check out.
|
||||||
# not enough bytes in the telegram. When the protocol/dvparser is improved, a replacement telegram should be placed here.
|
# Since the simulation will not remove the crcs unless they all check out, this will result in a broken telegram.
|
||||||
telegram=|3444EE4D813929271608|811D|7A51000000|046D1912A62B036E000000|5170426CE1F1436E00000002FF2C00000259D6D0D4090265FC0902FD66A00044C4|
|
telegram=|3444EE4D813929271608|811D|7A51000000|046D1912A62B036E000000|5170426CE1F1436E00000002FF2C00000259D6D0D4090265FC0902FD66A00044|
|
||||||
|
|
|
@ -0,0 +1,3 @@
|
||||||
|
# These telegrams have their dll crc:s still inside.
|
||||||
|
telegram=|734414867CC30B0003030D58A00EDF0700DC41343CEA390306FF0A0D44EADF07000DDF07000DDF07000DDF07000E44F9DF07000EDF07000EDF07000EDF07000E931EDF07000DDF07000DDF07000DDF0700035A4500000000374F0B20000000000000243412B31C07050C12280000000000002C002302062F19080F2F000000000000DCF5|
|
||||||
|
telegram=|3444EE4D813929271608|811D|7A51000000|046D1912A62B036E000000|5170426CE1F1436E00000002FF2C00000259D6D0D4090265FC0902FD66A00044C4|
|
109
src/wmbus.cc
109
src/wmbus.cc
|
@ -4060,14 +4060,20 @@ LIST_OF_AFL_AUTH_TYPES
|
||||||
return AFLAuthenticationType::Reserved1;
|
return AFLAuthenticationType::Reserved1;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool trimCRCsFrameFormatA(std::vector<uchar> &payload)
|
bool trimCRCsFrameFormatAInternal(std::vector<uchar> &payload, bool fail_is_ok)
|
||||||
{
|
{
|
||||||
if (payload.size() < 12) {
|
if (payload.size() < 12) {
|
||||||
debug("(wmbus) not enough bytes! expected at least 12 but got (%zu)!\n", payload.size());
|
if (!fail_is_ok)
|
||||||
|
{
|
||||||
|
debug("(wmbus) not enough bytes! expected at least 12 but got (%zu)!\n", payload.size());
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
size_t len = payload.size();
|
size_t len = payload.size();
|
||||||
debugPayload("(wmbus) trimming frame A", payload);
|
if (!fail_is_ok)
|
||||||
|
{
|
||||||
|
debugPayload("(wmbus) trimming frame A", payload);
|
||||||
|
}
|
||||||
|
|
||||||
vector<uchar> out;
|
vector<uchar> out;
|
||||||
|
|
||||||
|
@ -4080,7 +4086,10 @@ bool trimCRCsFrameFormatA(std::vector<uchar> &payload)
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
out.insert(out.end(), payload.begin(), payload.begin()+10);
|
out.insert(out.end(), payload.begin(), payload.begin()+10);
|
||||||
debug("(wmbus) ff a dll crc 0-%zu %04x ok\n", 10-1, calc_crc);
|
if (!fail_is_ok)
|
||||||
|
{
|
||||||
|
debug("(wmbus) ff a dll crc 0-%zu %04x ok\n", 10-1, calc_crc);
|
||||||
|
}
|
||||||
|
|
||||||
size_t pos = 12;
|
size_t pos = 12;
|
||||||
for (pos = 12; pos+18 <= len; pos += 18)
|
for (pos = 12; pos+18 <= len; pos += 18)
|
||||||
|
@ -4090,12 +4099,18 @@ bool trimCRCsFrameFormatA(std::vector<uchar> &payload)
|
||||||
check_crc = payload[to] << 8 | payload[to+1];
|
check_crc = payload[to] << 8 | payload[to+1];
|
||||||
if (calc_crc != check_crc && !FUZZING)
|
if (calc_crc != check_crc && !FUZZING)
|
||||||
{
|
{
|
||||||
debug("(wmbus) ff a dll crc mid (calculated %04x) did not match (expected %04x) for bytes %zu-%zu!\n",
|
if (!fail_is_ok)
|
||||||
calc_crc, check_crc, pos, to-1);
|
{
|
||||||
|
debug("(wmbus) ff a dll crc mid (calculated %04x) did not match (expected %04x) for bytes %zu-%zu!\n",
|
||||||
|
calc_crc, check_crc, pos, to-1);
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
out.insert(out.end(), payload.begin()+pos, payload.begin()+pos+16);
|
out.insert(out.end(), payload.begin()+pos, payload.begin()+pos+16);
|
||||||
debug("(wmbus) ff a dll crc mid %zu-%zu %04x ok\n", pos, to-1, calc_crc);
|
if (!fail_is_ok)
|
||||||
|
{
|
||||||
|
debug("(wmbus) ff a dll crc mid %zu-%zu %04x ok\n", pos, to-1, calc_crc);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pos < len-2)
|
if (pos < len-2)
|
||||||
|
@ -4106,12 +4121,23 @@ bool trimCRCsFrameFormatA(std::vector<uchar> &payload)
|
||||||
check_crc = payload[tto] << 8 | payload[tto+1];
|
check_crc = payload[tto] << 8 | payload[tto+1];
|
||||||
if (calc_crc != check_crc && !FUZZING)
|
if (calc_crc != check_crc && !FUZZING)
|
||||||
{
|
{
|
||||||
debug("(wmbus) ff a dll crc final (calculated %04x) did not match (expected %04x) for bytes %zu-%zu!\n",
|
if (!fail_is_ok)
|
||||||
calc_crc, check_crc, pos, tto-1);
|
{
|
||||||
|
debug("(wmbus) ff a dll crc final (calculated %04x) did not match (expected %04x) for bytes %zu-%zu!\n",
|
||||||
|
calc_crc, check_crc, pos, tto-1);
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
out.insert(out.end(), payload.begin()+pos, payload.begin()+tto);
|
out.insert(out.end(), payload.begin()+pos, payload.begin()+tto);
|
||||||
debug("(wmbus) ff a dll crc final %zu-%zu %04x ok\n", pos, tto-1, calc_crc);
|
if (!fail_is_ok)
|
||||||
|
{
|
||||||
|
debug("(wmbus) ff a dll crc final %zu-%zu %04x ok\n", pos, tto-1, calc_crc);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (fail_is_ok)
|
||||||
|
{
|
||||||
|
debugPayload("(wmbus) trimming frame A", payload);
|
||||||
}
|
}
|
||||||
|
|
||||||
out[0] = out.size()-1;
|
out[0] = out.size()-1;
|
||||||
|
@ -4120,20 +4146,26 @@ bool trimCRCsFrameFormatA(std::vector<uchar> &payload)
|
||||||
payload = out;
|
payload = out;
|
||||||
size_t new_size = payload.size();
|
size_t new_size = payload.size();
|
||||||
|
|
||||||
debug("(wmbus) trimmed %zu crc bytes from frame a and ignored %zu suffix bytes.\n", (len-new_len), (old_size-new_size)-(len-new_len));
|
debug("(wmbus) trimmed %zu dll crc bytes from frame a and ignored %zu suffix bytes.\n", (len-new_len), (old_size-new_size)-(len-new_len));
|
||||||
debugPayload("(wmbus) trimmed frame A", payload);
|
debugPayload("(wmbus) trimmed frame A", payload);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool trimCRCsFrameFormatB(std::vector<uchar> &payload)
|
bool trimCRCsFrameFormatBInternal(std::vector<uchar> &payload, bool fail_is_ok)
|
||||||
{
|
{
|
||||||
if (payload.size() < 12) {
|
if (payload.size() < 12) {
|
||||||
debug("(wmbus) not enough bytes! expected at least 12 but got (%zu)!\n", payload.size());
|
if (!fail_is_ok)
|
||||||
|
{
|
||||||
|
debug("(wmbus) not enough bytes! expected at least 12 but got (%zu)!\n", payload.size());
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
size_t len = payload.size();
|
size_t len = payload.size();
|
||||||
debugPayload("(wmbus) trimming frame B", payload);
|
if (!fail_is_ok)
|
||||||
|
{
|
||||||
|
debugPayload("(wmbus) trimming frame B", payload);
|
||||||
|
}
|
||||||
|
|
||||||
vector<uchar> out;
|
vector<uchar> out;
|
||||||
size_t crc1_pos, crc2_pos;
|
size_t crc1_pos, crc2_pos;
|
||||||
|
@ -4153,12 +4185,18 @@ bool trimCRCsFrameFormatB(std::vector<uchar> &payload)
|
||||||
|
|
||||||
if (calc_crc != check_crc && !FUZZING)
|
if (calc_crc != check_crc && !FUZZING)
|
||||||
{
|
{
|
||||||
debug("(wmbus) ff b dll crc (calculated %04x) did not match (expected %04x) for bytes 0-%zu!\n", calc_crc, check_crc, crc1_pos);
|
if (!fail_is_ok)
|
||||||
|
{
|
||||||
|
debug("(wmbus) ff b dll crc (calculated %04x) did not match (expected %04x) for bytes 0-%zu!\n", calc_crc, check_crc, crc1_pos);
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
out.insert(out.end(), payload.begin(), payload.begin()+crc1_pos);
|
out.insert(out.end(), payload.begin(), payload.begin()+crc1_pos);
|
||||||
debug("(wmbus) ff b dll crc first 0-%zu %04x ok\n", crc1_pos, calc_crc);
|
if (!fail_is_ok)
|
||||||
|
{
|
||||||
|
debug("(wmbus) ff b dll crc first 0-%zu %04x ok\n", crc1_pos, calc_crc);
|
||||||
|
}
|
||||||
|
|
||||||
if (crc2_pos > 0)
|
if (crc2_pos > 0)
|
||||||
{
|
{
|
||||||
|
@ -4167,13 +4205,24 @@ bool trimCRCsFrameFormatB(std::vector<uchar> &payload)
|
||||||
|
|
||||||
if (calc_crc != check_crc && !FUZZING)
|
if (calc_crc != check_crc && !FUZZING)
|
||||||
{
|
{
|
||||||
debug("(wmbus) ff b dll crc (calculated %04x) did not match (expected %04x) for bytes %zu-%zu!\n",
|
if (!fail_is_ok)
|
||||||
calc_crc, check_crc, crc1_pos+2, crc2_pos);
|
{
|
||||||
|
debug("(wmbus) ff b dll crc (calculated %04x) did not match (expected %04x) for bytes %zu-%zu!\n",
|
||||||
|
calc_crc, check_crc, crc1_pos+2, crc2_pos);
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
out.insert(out.end(), payload.begin()+crc1_pos+2, payload.begin()+crc2_pos);
|
out.insert(out.end(), payload.begin()+crc1_pos+2, payload.begin()+crc2_pos);
|
||||||
debug("(wmbus) ff b dll crc final %zu-%zu %04x ok\n", crc1_pos+2, crc2_pos, calc_crc);
|
if (!fail_is_ok)
|
||||||
|
{
|
||||||
|
debug("(wmbus) ff b dll crc final %zu-%zu %04x ok\n", crc1_pos+2, crc2_pos, calc_crc);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (fail_is_ok)
|
||||||
|
{
|
||||||
|
debugPayload("(wmbus) trimming frame B", payload);
|
||||||
}
|
}
|
||||||
|
|
||||||
out[0] = out.size()-1;
|
out[0] = out.size()-1;
|
||||||
|
@ -4182,12 +4231,28 @@ bool trimCRCsFrameFormatB(std::vector<uchar> &payload)
|
||||||
payload = out;
|
payload = out;
|
||||||
size_t new_size = payload.size();
|
size_t new_size = payload.size();
|
||||||
|
|
||||||
debug("(wmbus) trimmed %zu crc bytes from frame b and ignored %zu suffix bytes.\n", (len-new_len), (old_size-new_size)-(len-new_len));
|
debug("(wmbus) trimmed %zu dll crc bytes from frame b and ignored %zu suffix bytes.\n", (len-new_len), (old_size-new_size)-(len-new_len));
|
||||||
debugPayload("(wmbus) trimmed frame B", payload);
|
debugPayload("(wmbus) trimmed frame B", payload);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void removeAnyDLLCRCs(std::vector<uchar> &payload)
|
||||||
|
{
|
||||||
|
bool trimmed = trimCRCsFrameFormatAInternal(payload, true);
|
||||||
|
if (!trimmed) trimCRCsFrameFormatBInternal(payload, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool trimCRCsFrameFormatA(std::vector<uchar> &payload)
|
||||||
|
{
|
||||||
|
return trimCRCsFrameFormatAInternal(payload, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool trimCRCsFrameFormatB(std::vector<uchar> &payload)
|
||||||
|
{
|
||||||
|
return trimCRCsFrameFormatBInternal(payload, false);
|
||||||
|
}
|
||||||
|
|
||||||
FrameStatus checkWMBusFrame(vector<uchar> &data,
|
FrameStatus checkWMBusFrame(vector<uchar> &data,
|
||||||
size_t *frame_length,
|
size_t *frame_length,
|
||||||
int *payload_len_out,
|
int *payload_len_out,
|
||||||
|
|
|
@ -27,6 +27,7 @@
|
||||||
|
|
||||||
// Check and remove the data link layer CRCs from a wmbus telegram.
|
// Check and remove the data link layer CRCs from a wmbus telegram.
|
||||||
// If the CRCs do not pass the test, return false.
|
// If the CRCs do not pass the test, return false.
|
||||||
|
void removeAnyDLLCRCs(std::vector<uchar> &payload);
|
||||||
bool trimCRCsFrameFormatA(std::vector<uchar> &payload);
|
bool trimCRCsFrameFormatA(std::vector<uchar> &payload);
|
||||||
bool trimCRCsFrameFormatB(std::vector<uchar> &payload);
|
bool trimCRCsFrameFormatB(std::vector<uchar> &payload);
|
||||||
|
|
||||||
|
|
|
@ -175,6 +175,13 @@ void WMBusSimulator::simulate()
|
||||||
error("Not a valid string of hex bytes! \"%s\"\n", l.c_str());
|
error("Not a valid string of hex bytes! \"%s\"\n", l.c_str());
|
||||||
}
|
}
|
||||||
AboutTelegram about("", 0, FrameType::WMBUS);
|
AboutTelegram about("", 0, FrameType::WMBUS);
|
||||||
|
// Since this is a simulation, try to remove any frame format A or B
|
||||||
|
// data link layer crcs. These might remain if we have received the telegram
|
||||||
|
// to be simulated, from a CUL device or some other devices that does not remove the crcs.
|
||||||
|
// Normally the dongle (im871a/amb8465/rc1180/rtlwmbus/rtl443) removes the dll-crcs.
|
||||||
|
// Removing dll-crcs are also done explicitly in the wmbus_cul.cc driver.
|
||||||
|
removeAnyDLLCRCs(payload);
|
||||||
|
|
||||||
handleTelegram(about, payload);
|
handleTelegram(about, payload);
|
||||||
}
|
}
|
||||||
manager_->stop();
|
manager_->stop();
|
||||||
|
|
3
test.sh
3
test.sh
|
@ -114,6 +114,9 @@ if [ "$?" != "0" ]; then RC="1"; fi
|
||||||
./tests/test_hex_cmdline.sh $PROG
|
./tests/test_hex_cmdline.sh $PROG
|
||||||
if [ "$?" != "0" ]; then RC="1"; fi
|
if [ "$?" != "0" ]; then RC="1"; fi
|
||||||
|
|
||||||
|
./tests/test_removing_dll_crcs.sh $PROG
|
||||||
|
if [ "$?" != "0" ]; then RC="1"; fi
|
||||||
|
|
||||||
./tests/test_broken.sh $PROG
|
./tests/test_broken.sh $PROG
|
||||||
if [ "$?" != "0" ]; then RC="1"; fi
|
if [ "$?" != "0" ]; then RC="1"; fi
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,37 @@
|
||||||
|
#!/bin/sh
|
||||||
|
|
||||||
|
PROG="$1"
|
||||||
|
TEST=testoutput
|
||||||
|
mkdir -p $TEST
|
||||||
|
|
||||||
|
TESTNAME="Test auto removal of dll crcs in simulated telegrams"
|
||||||
|
TESTRESULT="ERROR"
|
||||||
|
|
||||||
|
cat > $TEST/test_expected.txt <<EOF
|
||||||
|
No meters configured. Printing id:s of all telegrams heard!
|
||||||
|
Received telegram from: 000bc37c
|
||||||
|
manufacturer: (APT) Unknown (0x8614)
|
||||||
|
type: Gas meter (0x03)
|
||||||
|
ver: 0x03
|
||||||
|
driver: apator08
|
||||||
|
Received telegram from: 27293981
|
||||||
|
manufacturer: (SON) Sontex, Switzerland (0x4dee)
|
||||||
|
type: Heat Cost Allocator (0x08)
|
||||||
|
ver: 0x16
|
||||||
|
driver: sontex868
|
||||||
|
EOF
|
||||||
|
|
||||||
|
$PROG simulations/simulation_dll_crcs.txt > $TEST/test_output.txt 2>&1
|
||||||
|
|
||||||
|
if [ "$?" = "0" ]
|
||||||
|
then
|
||||||
|
diff $TEST/test_expected.txt $TEST/test_output.txt
|
||||||
|
if [ "$?" = "0" ]
|
||||||
|
then
|
||||||
|
echo OK: $TESTNAME
|
||||||
|
TESTRESULT="OK"
|
||||||
|
fi
|
||||||
|
else
|
||||||
|
echo "wmbusmeters returned error code: $?"
|
||||||
|
cat $TEST/test_output.txt
|
||||||
|
fi
|
Ładowanie…
Reference in New Issue