From 0fccc0e337bcf0f49a238522a40fd51d405e5648 Mon Sep 17 00:00:00 2001 From: Michael Heimpold Date: Sat, 18 Jan 2014 13:44:01 +0100 Subject: [PATCH 1/2] Add a function to calculate the manufacturer ID from the 3 byte ASCII code. The formula can be found at http://www.m-bus.com/files/w4b21021.pdf, chapter 3.3 at page 6. This obsoletes the static defines, so remove them. Signed-off-by: Michael Heimpold --- mbus/mbus-protocol.c | 55 ++++++++++++++++++++++++++++---------------- mbus/mbus-protocol.h | 28 ++++------------------ 2 files changed, 39 insertions(+), 44 deletions(-) diff --git a/mbus/mbus-protocol.c b/mbus/mbus-protocol.c index 27b0354..852e28f 100755 --- a/mbus/mbus-protocol.c +++ b/mbus/mbus-protocol.c @@ -21,6 +21,21 @@ static char error_str[512]; #define NITEMS(x) (sizeof(x)/sizeof(x[0])) +//------------------------------------------------------------------------------ +// Return the manufacturer ID according to the manufacturer's 3 byte ASCII code +//------------------------------------------------------------------------------ +unsigned int +mbus_manufacturer_id(char *manufacturer) +{ + unsigned int id; + + id = (toupper(manufacturer[0]) - 64) * 32 * 32 + + (toupper(manufacturer[1]) - 64) * 32 + + (toupper(manufacturer[2]) - 64); + + return id; +} + //------------------------------------------------------------------------------ // internal data //------------------------------------------------------------------------------ @@ -809,7 +824,7 @@ mbus_data_product_name(mbus_data_variable_header *header) { manufacturer = (header->manufacturer[1] << 8) + header->manufacturer[0]; - if (manufacturer == MBUS_VARIABLE_DATA_MAN_ACW) + if (manufacturer == mbus_manufacturer_id("ACW")) { switch (header->version) { @@ -833,7 +848,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_EFE) + else if (manufacturer == mbus_manufacturer_id("EFE")) { switch (header->version) { @@ -845,7 +860,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_ELV) + else if (manufacturer == mbus_manufacturer_id("ELV")) { switch (header->version) { @@ -875,7 +890,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_GMC) + else if (manufacturer == mbus_manufacturer_id("GMC")) { switch (header->version) { @@ -884,7 +899,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_SLB) + else if (manufacturer == mbus_manufacturer_id("SLB")) { switch (header->version) { @@ -896,7 +911,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_HYD) + else if (manufacturer == mbus_manufacturer_id("HYD")) { switch (header->version) { @@ -905,7 +920,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_LUG) + else if (manufacturer == mbus_manufacturer_id("LUG")) { switch (header->version) { @@ -923,7 +938,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_RAM) + else if (manufacturer == mbus_manufacturer_id("RAM")) { switch (header->version) { @@ -932,7 +947,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_RKE) + else if (manufacturer == mbus_manufacturer_id("RKE")) { switch (header->version) { @@ -941,7 +956,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_SVM) + else if (manufacturer == mbus_manufacturer_id("SVM")) { switch (header->version) { @@ -953,7 +968,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_SON) + else if (manufacturer == mbus_manufacturer_id("SON")) { switch (header->version) { @@ -962,7 +977,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_LSE) + else if (manufacturer == mbus_manufacturer_id("LSE")) { switch (header->version) { @@ -971,7 +986,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_SEN) + else if (manufacturer == mbus_manufacturer_id("SEN")) { switch (header->version) { @@ -980,7 +995,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_SPX) + else if (manufacturer == mbus_manufacturer_id("SPX")) { switch (header->version) { @@ -990,7 +1005,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_ELS) + else if (manufacturer == mbus_manufacturer_id("ELS")) { switch (header->version) { @@ -999,7 +1014,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_NZR) + else if (manufacturer == mbus_manufacturer_id("NZR")) { switch (header->version) { @@ -1008,7 +1023,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_KAM) + else if (manufacturer == mbus_manufacturer_id("KAM")) { switch (header->version) { @@ -1020,7 +1035,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_EMH) + else if (manufacturer == mbus_manufacturer_id("EMH")) { switch (header->version) { @@ -1029,7 +1044,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_TCH) + else if (manufacturer == mbus_manufacturer_id("TCH")) { switch (header->version) { @@ -1038,7 +1053,7 @@ mbus_data_product_name(mbus_data_variable_header *header) break; } } - else if (manufacturer == MBUS_VARIABLE_DATA_MAN_ZRM) + else if (manufacturer == mbus_manufacturer_id("ZRM")) { switch (header->version) { diff --git a/mbus/mbus-protocol.h b/mbus/mbus-protocol.h index c63e089..29b1813 100755 --- a/mbus/mbus-protocol.h +++ b/mbus/mbus-protocol.h @@ -492,30 +492,10 @@ typedef struct _mbus_data_secondary_address { #define MBUS_VARIABLE_DATA_MEDIUM_PRESSURE 0x18 #define MBUS_VARIABLE_DATA_MEDIUM_ADC 0x19 -#define MBUS_VARIABLE_DATA_MAN_ACW 0x0477 -#define MBUS_VARIABLE_DATA_MAN_ABB 0x0442 -#define MBUS_VARIABLE_DATA_MAN_AMT 0x05B4 -#define MBUS_VARIABLE_DATA_MAN_EFE 0x14C5 -#define MBUS_VARIABLE_DATA_MAN_ELS 0x1593 -#define MBUS_VARIABLE_DATA_MAN_ELV 0x1596 -#define MBUS_VARIABLE_DATA_MAN_EMH 0x15A8 -#define MBUS_VARIABLE_DATA_MAN_GMC 0x1DA3 -#define MBUS_VARIABLE_DATA_MAN_HYD 0x2324 -#define MBUS_VARIABLE_DATA_MAN_KAM 0x2C2D -#define MBUS_VARIABLE_DATA_MAN_LSE 0x3265 -#define MBUS_VARIABLE_DATA_MAN_LUG 0x32A7 -#define MBUS_VARIABLE_DATA_MAN_NZR 0x3B52 -#define MBUS_VARIABLE_DATA_MAN_PAD 0x4024 -#define MBUS_VARIABLE_DATA_MAN_QDS 0x4493 -#define MBUS_VARIABLE_DATA_MAN_RAM 0x482D -#define MBUS_VARIABLE_DATA_MAN_RKE 0x4965 -#define MBUS_VARIABLE_DATA_MAN_SEN 0x4CAE -#define MBUS_VARIABLE_DATA_MAN_SLB 0x4D82 -#define MBUS_VARIABLE_DATA_MAN_SON 0x4DEE -#define MBUS_VARIABLE_DATA_MAN_SPX 0x4E18 -#define MBUS_VARIABLE_DATA_MAN_SVM 0x4ECD -#define MBUS_VARIABLE_DATA_MAN_TCH 0x5068 -#define MBUS_VARIABLE_DATA_MAN_ZRM 0x6A4D +// +// Return manufacturer ID +// +unsigned int mbus_manufacturer_id(char *manufacturer); // // Event callback functions From f262138572ea666a3970d8ae7f3f2be733e5c806 Mon Sep 17 00:00:00 2001 From: Michael Heimpold Date: Sat, 18 Jan 2014 20:43:57 +0100 Subject: [PATCH 2/2] mbus_manufacturer_id: add error checking code Signed-off-by: Michael Heimpold --- mbus/mbus-protocol.c | 24 ++++++++++++++++++++++-- mbus/mbus-protocol.h | 3 ++- 2 files changed, 24 insertions(+), 3 deletions(-) diff --git a/mbus/mbus-protocol.c b/mbus/mbus-protocol.c index 852e28f..29a6d77 100755 --- a/mbus/mbus-protocol.c +++ b/mbus/mbus-protocol.c @@ -22,18 +22,38 @@ static char error_str[512]; #define NITEMS(x) (sizeof(x)/sizeof(x[0])) //------------------------------------------------------------------------------ -// Return the manufacturer ID according to the manufacturer's 3 byte ASCII code +// Returns the manufacturer ID according to the manufacturer's 3 byte ASCII code +// or zero when there was an error. //------------------------------------------------------------------------------ unsigned int mbus_manufacturer_id(char *manufacturer) { unsigned int id; + /* + * manufacturer must consist of at least 3 alphabetic characters, + * additional chars are silently ignored. + */ + + if (!manufacturer || strlen(manufacturer) < 3) + return 0; + + if (!isalpha(manufacturer[0]) || + !isalpha(manufacturer[1]) || + !isalpha(manufacturer[2])) + return 0; + id = (toupper(manufacturer[0]) - 64) * 32 * 32 + (toupper(manufacturer[1]) - 64) * 32 + (toupper(manufacturer[2]) - 64); - return id; + /* + * Valid input data should be in the range of 'AAA' to 'ZZZ' according to + * the FLAG Association (http://www.dlms.com/flag/), thus resulting in + * an ID from 0x0421 to 0x6b5a. If the conversion results in anything not + * in this range, simply discard it and return 0 instead. + */ + return (0x0421 <= id && id <= 0x6b5a) ? id : 0; } //------------------------------------------------------------------------------ diff --git a/mbus/mbus-protocol.h b/mbus/mbus-protocol.h index 29b1813..3fb39f0 100755 --- a/mbus/mbus-protocol.h +++ b/mbus/mbus-protocol.h @@ -493,7 +493,8 @@ typedef struct _mbus_data_secondary_address { #define MBUS_VARIABLE_DATA_MEDIUM_ADC 0x19 // -// Return manufacturer ID +// Returns the manufacturer ID or zero if the given +// string could not be converted into an ID // unsigned int mbus_manufacturer_id(char *manufacturer);