diff --git a/ChangeLog.md b/ChangeLog.md index e3a6e2e7..83ac7ccd 100644 --- a/ChangeLog.md +++ b/ChangeLog.md @@ -2,6 +2,7 @@ ## Bug Fixes * fix for device string symlink with colon * fix "read" and "write" command response +* fix dump of divisor # 24.1 (2024-10-27) diff --git a/src/ebusd/bushandler.cpp b/src/ebusd/bushandler.cpp index 5dc2e060..2db31899 100644 --- a/src/ebusd/bushandler.cpp +++ b/src/ebusd/bushandler.cpp @@ -191,7 +191,7 @@ bool decodeType(const DataType* type, const SymbolString& input, size_t length, first = false; *output << endl << " "; ostringstream::pos_type cnt = output->tellp(); - type->dump(OF_NONE, length, false, output); + type->dump(OF_NONE, length, ad_none, output); cnt = output->tellp() - cnt; while (cnt < 5) { *output << " "; diff --git a/src/ebusd/main.cpp b/src/ebusd/main.cpp index 43437de5..b5edc564 100644 --- a/src/ebusd/main.cpp +++ b/src/ebusd/main.cpp @@ -394,7 +394,7 @@ int main(int argc, char* argv[], char* envp[]) { } if (s_opt.dumpConfig & OF_JSON) { *out << "{\"datatypes\":["; - DataTypeList::getInstance()->dump(s_opt.dumpConfig, true, out); + DataTypeList::getInstance()->dump(s_opt.dumpConfig, out); *out << "],\"templates\":["; const auto tmpl = s_scanHelper->getTemplates(""); tmpl->dump(s_opt.dumpConfig, out); diff --git a/src/ebusd/mainloop.cpp b/src/ebusd/mainloop.cpp index 7de1313b..ab2f66b3 100644 --- a/src/ebusd/mainloop.cpp +++ b/src/ebusd/mainloop.cpp @@ -2279,7 +2279,7 @@ result_t MainLoop::executeGet(const vector& args, bool* connected, ostri if (uri == "/datatypes") { *ostream << "["; OutputFormat verbosity = OF_NAMES|OF_JSON|OF_ALL_ATTRS; - DataTypeList::getInstance()->dump(verbosity, true, ostream); + DataTypeList::getInstance()->dump(verbosity, ostream); *ostream << "\n]"; type = 6; *connected = false; diff --git a/src/lib/ebus/data.cpp b/src/lib/ebus/data.cpp index ca7c36d5..9f236166 100644 --- a/src/lib/ebus/data.cpp +++ b/src/lib/ebus/data.cpp @@ -555,7 +555,7 @@ void SingleDataField::dumpPrefix(bool prependFieldSeparator, OutputFormat output } *output << FIELD_SEPARATOR; } - m_dataType->dump(outputFormat, m_length, true, output); + m_dataType->dump(outputFormat, m_length, ad_normal, output); } void SingleDataField::dumpSuffix(OutputFormat outputFormat, ostream* output) const { diff --git a/src/lib/ebus/datatype.cpp b/src/lib/ebus/datatype.cpp index 021ec65e..3f1d6b12 100755 --- a/src/lib/ebus/datatype.cpp +++ b/src/lib/ebus/datatype.cpp @@ -124,7 +124,7 @@ uint16_t floatToUint16(float value) { return static_cast((shift << 11) | (negative ? 0x8000 | (0x800-sig) : sig)); } -bool DataType::dump(OutputFormat outputFormat, size_t length, bool appendDivisor, ostream* output) const { +bool DataType::dump(OutputFormat outputFormat, size_t length, AppendDivisor appendDivisor, ostream* output) const { if (outputFormat & OF_JSON) { *output << "\"type\": \"" << m_id << "\", \"isbits\": " << (getBitCount() < 8 ? "true" : "false"); @@ -149,7 +149,7 @@ bool DataType::dump(OutputFormat outputFormat, size_t length, bool appendDivisor *output << static_cast(length); } } - if (appendDivisor) { + if (appendDivisor != ad_none) { *output << FIELD_SEPARATOR; } } @@ -157,7 +157,7 @@ bool DataType::dump(OutputFormat outputFormat, size_t length, bool appendDivisor } -bool StringDataType::dump(OutputFormat outputFormat, size_t length, bool appendDivisor, ostream* output) const { +bool StringDataType::dump(OutputFormat outputFormat, size_t length, AppendDivisor appendDivisor, ostream* output) const { DataType::dump(outputFormat, length, appendDivisor, output); if ((outputFormat & OF_JSON) && (outputFormat & OF_ALL_ATTRS)) { *output << ", \"result\": \"" << (isIgnored() ? "void" : "string") << "\""; @@ -300,7 +300,7 @@ result_t StringDataType::writeSymbols(size_t offset, size_t length, istringstrea } -bool DateTimeDataType::dump(OutputFormat outputFormat, size_t length, bool appendDivisor, ostream* output) const { +bool DateTimeDataType::dump(OutputFormat outputFormat, size_t length, AppendDivisor appendDivisor, ostream* output) const { DataType::dump(outputFormat, length, appendDivisor, output); if ((outputFormat & OF_JSON) && (outputFormat & OF_ALL_ATTRS)) { *output << ", \"result\": \"" << (hasDate() ? hasTime() ? "datetime" : "date" : "time") << "\""; @@ -672,7 +672,7 @@ size_t NumberDataType::calcPrecision(int divisor) { return precision; } -bool NumberDataType::dump(OutputFormat outputFormat, size_t length, bool appendDivisor, ostream* output) const { +bool NumberDataType::dump(OutputFormat outputFormat, size_t length, AppendDivisor appendDivisor, ostream* output) const { if (m_bitCount < 8) { DataType::dump(outputFormat, m_bitCount, appendDivisor, output); } else { @@ -681,11 +681,17 @@ bool NumberDataType::dump(OutputFormat outputFormat, size_t length, bool appendD if ((outputFormat & OF_JSON) && (outputFormat & OF_ALL_ATTRS)) { *output << ", \"result\": \"number\""; } - if (!appendDivisor) { + if (appendDivisor == ad_none) { return false; } bool ret = false; - if (m_baseType) { + if (appendDivisor == ad_full && m_divisor != 1) { + if (outputFormat & OF_JSON) { + *output << ", \"divisor\": "; + } + *output << m_divisor; + ret = true; + } else if (m_baseType) { if (m_baseType->m_divisor != m_divisor) { if (outputFormat & OF_JSON) { *output << ", \"divisor\": "; @@ -693,12 +699,6 @@ bool NumberDataType::dump(OutputFormat outputFormat, size_t length, bool appendD *output << (m_divisor / m_baseType->m_divisor); ret = true; } - } else if (m_divisor != 1) { - if (outputFormat & OF_JSON) { - *output << ", \"divisor\": "; - } - *output << m_divisor; - ret = true; } if (ret && (outputFormat & OF_JSON) && (outputFormat & OF_ALL_ATTRS)) { *output << ", \"precision\": " << static_cast(getPrecision()); @@ -1317,7 +1317,7 @@ DataTypeList* DataTypeList::getInstance() { return &s_instance; } -void DataTypeList::dump(OutputFormat outputFormat, bool appendDivisor, ostream* output) const { +void DataTypeList::dump(OutputFormat outputFormat, ostream* output) const { bool json = outputFormat & OF_JSON; string sep = "\n"; for (const auto &it : m_typesById) { @@ -1329,9 +1329,9 @@ void DataTypeList::dump(OutputFormat outputFormat, bool appendDivisor, ostream* *output << sep << " {"; } if ((dataType->getBitCount() % 8) != 0) { - dataType->dump(outputFormat, dataType->getBitCount(), appendDivisor, output); + dataType->dump(outputFormat, dataType->getBitCount(), ad_full, output); } else { - dataType->dump(outputFormat, dataType->getBitCount() / 8, appendDivisor, output); + dataType->dump(outputFormat, dataType->getBitCount() / 8, ad_full, output); } if (json) { *output << "}"; diff --git a/src/lib/ebus/datatype.h b/src/lib/ebus/datatype.h index 013d2f70..f6bd1a23 100755 --- a/src/lib/ebus/datatype.h +++ b/src/lib/ebus/datatype.h @@ -137,6 +137,13 @@ constexpr inline enum OutputFormat operator~ (enum OutputFormat self) { return (enum OutputFormat)(~(OutputFormatBaseType)self); } +/** whether divisor should be appended to a dump. */ +enum AppendDivisor { + ad_none, //!< no dump of divisor + ad_normal, //!< regular dump of divisor (i.e. not for base types) + ad_full, //!< full dump of divisor (i.e. also for base types) +}; + /** the message part in which a data field is stored. */ enum PartType { pt_any, //!< stored in any data (master or slave) @@ -286,7 +293,7 @@ class DataType { * @param output the @a ostream to dump to. * @return true when a non-default divisor was written to the output. */ - virtual bool dump(OutputFormat outputFormat, size_t length, bool appendDivisor, ostream* output) const; + virtual bool dump(OutputFormat outputFormat, size_t length, AppendDivisor appendDivisor, ostream* output) const; /** * Internal method for reading the numeric raw value from a @a SymbolString. @@ -363,7 +370,7 @@ class StringDataType : public DataType { virtual ~StringDataType() {} // @copydoc - bool dump(OutputFormat outputFormat, size_t length, bool appendDivisor, ostream* output) const override; + bool dump(OutputFormat outputFormat, size_t length, AppendDivisor appendDivisor, ostream* output) const override; // @copydoc result_t readRawValue(size_t offset, size_t length, const SymbolString& input, @@ -410,7 +417,7 @@ class DateTimeDataType : public DataType { virtual ~DateTimeDataType() {} // @copydoc - bool dump(OutputFormat outputFormat, size_t length, bool appendDivisor, ostream* output) const override; + bool dump(OutputFormat outputFormat, size_t length, AppendDivisor appendDivisor, ostream* output) const override; /** * @return true if date part is present. @@ -503,7 +510,7 @@ class NumberDataType : public DataType { static size_t calcPrecision(int divisor); // @copydoc - bool dump(OutputFormat outputFormat, size_t length, bool appendDivisor, ostream* output) const override; + bool dump(OutputFormat outputFormat, size_t length, AppendDivisor appendDivisor, ostream* output) const override; /** * Derive a new @a NumberDataType from this. @@ -658,10 +665,9 @@ class DataTypeList { /** * Dump the type list optionally including the divisor to the output. * @param outputFormat the @a OutputFormat options. - * @param appendDivisor whether to append the divisor (if available). * @param output the @a ostream to dump to. */ - void dump(OutputFormat outputFormat, bool appendDivisor, ostream* output) const; + void dump(OutputFormat outputFormat, ostream* output) const; /** * Removes all @a DataType instances. diff --git a/src/lib/ebus/test/test_message.cpp b/src/lib/ebus/test/test_message.cpp index ea5ceb44..dda4ee90 100644 --- a/src/lib/ebus/test/test_message.cpp +++ b/src/lib/ebus/test/test_message.cpp @@ -221,6 +221,8 @@ int main() { " ]\n" " }: \n" " \"field\": {\"value\": 42, \"raw\": [42]}", "ff75b509030d0100", "012a", "jNr"}, + {"r,CIRCUIT,NAME,COMMENT,,,,0100,field,,temp", "r,cirCIRCUITcuit,naNAMEme,comCOMMENTment,ff,75,b509,0d0100,field,s,D2C,,°C,Temperatur: field=42.00 °C [Temperatur]", "ff75b509030d0100", "02a002", "DN"}, + {"r,CIRCUIT,NAME,COMMENT,,,,0100,field,,D2C,,°C,Temperatur", "r,cirCIRCUITcuit,naNAMEme,comCOMMENTment,ff,75,b509,0d0100,field,s,D2C,,°C,Temperatur: field=42.00 °C [Temperatur]", "ff75b509030d0100", "02a002", "DN"}, }; templates = new DataFieldTemplates(); unsigned int lineNo = 0;