|
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133 |
- #include "dbcc/dbc_iterator.h"
-
- #include <fstream>
- #include <limits>
-
- namespace ad {
- namespace dbcc {
-
- constexpr const char* kPreambleNode = "BU_";
- constexpr const char* kPreambleValueTable = "VAL_TABLE_";
- constexpr const char* kPreambleMessage = "BO_";
- constexpr const char* kPreambleSignal = "SG_";
- constexpr const char* kPreambleComment = "CM_";
- constexpr const char* kPreambleAttribute = "BA_";
- constexpr const char* kPreambleAttributeDefinition = "BA_DEF_";
- constexpr const char* kPreambleEnvironmentVariable = "EV_";
-
- DbcIterator::DbcIterator(const std::string& filePath)
- {
- std::ifstream file(filePath);
- if (file) {
- Parse(file);
- }
- file.close();
- }
-
- DbcIterator::DbcIterator(std::istream& stream)
- {
- Parse(stream);
- }
-
- std::ostream& operator<<(std::ostream& out, DbcIterator& dbc)
- {
- for (auto& msg : dbc) {
- out << msg.Name() << " " << msg.Id() << std::endl;
- for (auto& sig : msg) {
- out << "Signal: " << sig.Name() << " [" << (sig.IsFloat() ? "float" : "int") << "] ";
- out << "To: ";
- for (auto to : sig.To()) {
- out << to << ", ";
- }
- out << sig.StartBit() << "," << sig.Length() << std::endl;
- out << "(" << sig.Factor() << ", " << sig.Offset() << ")" << std::endl;
- out << "[" << sig.Minimum() << ", " << sig.Maximum() << "]" << std::endl;
- if (sig.GetMultiplexor() == Multiplexor::kMultiplexed) {
- out << "#" << sig.MultiplexedNumber() << "#" << std::endl;
- } else if (sig.GetMultiplexor() == Multiplexor::kMultiplexor) {
- out << "+Multiplexor+" << std::endl;
- }
- out << std::endl;
- }
- }
- return out;
- }
-
- inline std::string ExtractQuotedContent(std::istream& is)
- {
- std::string content;
- char ch;
- bool in_quotes = false;
-
- while (is.good()) {
- is >> std::noskipws >> ch;
-
- if (ch == '"') {
- if (in_quotes) {
- break;
- } else {
- in_quotes = true;
- continue;
- }
- }
-
- if (in_quotes) {
- content.push_back(ch);
- }
- }
-
- return content;
- }
-
- void DbcIterator::Parse(std::istream& stream)
- {
- /**
- * Here I will guarantee each parser will always process to the EOL.
- * So the preamble will always be the first word also.
- */
- std::string preamble;
- messages_.clear();
-
- do {
- stream >> preamble;
-
- if (preamble == kPreambleMessage) {
- Message msg;
- stream >> msg;
- if (stream.fail()) {
- stream.clear();
- stream.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
- }
-
- if (msg.SignalCount() > 0) {
- messages_.emplace_back(msg);
- message_index_[msg.Id()] = static_cast<uint32_t>(messages_.size() - 1);
- }
- } else if (preamble == kPreambleComment) {
- // TODO(anjingyu): Parse the comment
- // std::cout << "[W] CM_ is unsupported now, ignore!" << std::endl;
- stream.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
- } else if (preamble == kPreambleValueTable) {
- // std::cout << "[W] VAL_TABLE_ is unsupported now, ignore!" << std::endl;
- stream.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
- } else if (preamble == kPreambleAttribute) {
- // std::cout << "[W] BA_ is unsupported now, ignore!" << std::endl;
- stream.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
- } else if (preamble == kPreambleAttributeDefinition) {
- // std::cout << "[W] BA_DEF_ is unsupported now, ignore!" << std::endl;
- stream.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
- } else if (preamble == kPreambleEnvironmentVariable) {
- // std::cout << "[W] EV_ is unsupported now, ignore!" << std::endl;
- stream.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
- } else if (preamble == kPreambleNode) {
- // std::cout << "[W] BU_ is unsupported now, ignore!" << std::endl;
- stream.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
- } else {
- // std::cout << "[W] " << preamble << " is unsupported now, ignore!" << std::endl;
- stream.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
- }
- } while (!stream.eof());
- }
-
- } // namespace dbcc
- } // namespace ad
|