diff --git a/.gitignore b/.gitignore index 119040b6..69207eca 100644 --- a/.gitignore +++ b/.gitignore @@ -11,14 +11,15 @@ Makefile.in .deps/ *.o *.dirstamp -/src/libcore/libcore.a -/src/libebus/libebus.a /src/ebusd/ebusd -/src/tools/ebusctl -/src/test/test_bus -/src/test/test_port -/src/test/test_configfile -/src/test/test_commands -/src/test/test_decode -/src/test/test_encode -/src/test/test_symbol +/src/ebusctl/ebusctl +/src/lib/utils/libutils.a +/src/lib/ebus/libebus.a +/src/lib/ebus/test/test_bus +/src/lib/ebus/test/test_port +/src/lib/ebus/test/test_configfile +/src/lib/ebus/test/test_commands +/src/lib/ebus/test/test_decode +/src/lib/ebus/test/test_encode +/src/lib/ebus/test/test_symbol +/src/lib/ebus/test/test_data diff --git a/Makefile.am b/Makefile.am index 7146e27c..2bf1f2d5 100644 --- a/Makefile.am +++ b/Makefile.am @@ -1,4 +1,4 @@ -SUBDIRS = src/libebus src/test src/libcore src/ebusd src/tools +SUBDIRS = src/lib/ebus src/lib/ebus/test src/lib/utils src/ebusd src/ebusctl distclean-local: -rm -rf autom4te.cache diff --git a/configure.ac b/configure.ac index 91356aaa..37d4ab21 100644 --- a/configure.ac +++ b/configure.ac @@ -7,11 +7,11 @@ AC_CONFIG_AUX_DIR([build]) AC_CONFIG_SRCDIR([src/ebusd/main.cpp]) AC_CONFIG_HEADERS([config.h]) AC_CONFIG_FILES([Makefile - src/libebus/Makefile - src/test/Makefile - src/libcore/Makefile + src/lib/ebus/Makefile + src/lib/ebus/test/Makefile + src/lib/utils/Makefile src/ebusd/Makefile - src/tools/Makefile]) + src/ebusctl/Makefile]) AM_INIT_AUTOMAKE([1.11 -Wall -Werror foreign]) diff --git a/src/ebusctl/Makefile.am b/src/ebusctl/Makefile.am new file mode 100644 index 00000000..5b5088ce --- /dev/null +++ b/src/ebusctl/Makefile.am @@ -0,0 +1,17 @@ +AM_CXXFLAGS = -fpic \ + -Wall \ + -Wextra \ + -I$(top_srcdir)/src/lib/utils \ + -I$(top_srcdir)/src/lib/ebus + +bin_PROGRAMS = ebusctl + +ebusctl_SOURCES = ebusctl.cpp + +ebusctl_LDADD = $(top_srcdir)/src/lib/utils/libutils.a \ + $(top_srcdir)/src/lib/ebus/libebus.a + +distclean-local: + -rm -f Makefile.in + -rm -rf .libs + diff --git a/src/tools/ebusctl.cpp b/src/ebusctl/ebusctl.cpp similarity index 100% rename from src/tools/ebusctl.cpp rename to src/ebusctl/ebusctl.cpp diff --git a/src/ebusd/Makefile.am b/src/ebusd/Makefile.am index a0990baf..742edf10 100644 --- a/src/ebusd/Makefile.am +++ b/src/ebusd/Makefile.am @@ -1,8 +1,8 @@ AM_CXXFLAGS = -fpic \ -Wall \ -Wextra \ - -I$(top_srcdir)/src/libcore \ - -I$(top_srcdir)/src/libebus + -I$(top_srcdir)/src/lib/utils \ + -I$(top_srcdir)/src/lib/ebus bin_PROGRAMS = ebusd @@ -17,8 +17,8 @@ ebusd_SOURCES = message.h \ baseloop.h \ main.cpp -ebusd_LDADD = $(top_srcdir)/src/libcore/libcore.a \ - $(top_srcdir)/src/libebus/libebus.a \ +ebusd_LDADD = $(top_srcdir)/src/lib/utils/libutils.a \ + $(top_srcdir)/src/lib/ebus/libebus.a \ -lpthread distclean-local: diff --git a/src/ebusd/baseloop.cpp b/src/ebusd/baseloop.cpp index b74e34ee..bf97f169 100644 --- a/src/ebusd/baseloop.cpp +++ b/src/ebusd/baseloop.cpp @@ -149,7 +149,7 @@ std::string BaseLoop::decodeMessage(const std::string& data) } std::string ebusCommand(A.getParam("p_address")); - ebusCommand += m_commands->getEbusCommand(index); + ebusCommand += m_commands->getEbusCommand(index, false); std::transform(ebusCommand.begin(), ebusCommand.end(), ebusCommand.begin(), tolower); BusCommand* busCommand = new BusCommand(ebusCommand, false); @@ -190,7 +190,7 @@ std::string BaseLoop::decodeMessage(const std::string& data) if (index >= 0) { std::string ebusCommand(A.getParam("p_address")); - ebusCommand += m_commands->getEbusCommand(index); + ebusCommand += m_commands->getEbusCommand(index, false); // encode data Command* command = new Command(index, (*m_commands)[index], cmd[3]); @@ -292,17 +292,6 @@ std::string BaseLoop::decodeMessage(const std::string& data) break; - case dump: - if (cmd.size() != 2) { - result << "usage: 'dump state' (state: on|off)"; - break; - } - - if (strcasecmp(cmd[1].c_str(), "ON") == 0) m_ebusloop->dump(true); - if (strcasecmp(cmd[1].c_str(), "OFF") == 0) m_ebusloop->dump(false); - result << "done"; - break; - case log: if (cmd.size () != 3 ) { result << "usage: 'log areas area,area,..' (areas: bas|net|bus|cyc|all)" << std::endl @@ -328,6 +317,26 @@ std::string BaseLoop::decodeMessage(const std::string& data) break; + case raw: + if (cmd.size() != 1) { + result << "usage: 'raw'"; + break; + } + + m_ebusloop->raw(); + result << "done"; + break; + + case dump: + if (cmd.size() != 1) { + result << "usage: 'dump'"; + break; + } + + m_ebusloop->dump(); + result << "done"; + break; + case reload: if (cmd.size() != 1) { result << "usage: 'reload'"; @@ -356,9 +365,10 @@ std::string BaseLoop::decodeMessage(const std::string& data) << " set - set ebus values 'set class cmd value'" << std::endl << " cyc - fetch cycle data 'cyc class cmd (sub)'" << std::endl << " hex - send given hex value 'hex type value' (value: ZZPBSBNNDx)" << std::endl << std::endl - << " dump - change dump state 'dump state' (state: on|off)" << std::endl << std::endl << " log - change log areas 'log areas area,area,..' (areas: bas|net|bus|cyc|all)" << std::endl << " - change log level 'log level level' (level: error|event|trace|debug)" << std::endl << std::endl + << " raw - toggle log raw data" << std::endl + << " dump - toggle dump state" << std::endl << std::endl << " reload - reload ebus configuration" << std::endl << std::endl << " stop - stop daemon" << std::endl << " quit - close connection" << std::endl << std::endl diff --git a/src/ebusd/baseloop.h b/src/ebusd/baseloop.h index f71649f2..9e68555c 100644 --- a/src/ebusd/baseloop.h +++ b/src/ebusd/baseloop.h @@ -46,16 +46,17 @@ private: WQueue m_queue; enum ClientCommand { - get, // get ebus data - set, // set ebus value - cyc, // fetch cycle data - hex, // send hex value - dump, // change dump state - log, // logger settings - reload, // reload ebus configuration - help, // print commands - notfound - }; + get, // get ebus data + set, // set ebus value + cyc, // fetch cycle data + hex, // send hex value + log, // logger settings + raw, // toggle log raw data + dump, // toggle dump state + reload, // reload ebus configuration + help, // print commands + notfound + }; ClientCommand getCase(const std::string& item) { @@ -63,8 +64,9 @@ private: if (strcasecmp(item.c_str(), "SET") == 0) return set; if (strcasecmp(item.c_str(), "CYC") == 0) return cyc; if (strcasecmp(item.c_str(), "HEX") == 0) return hex; - if (strcasecmp(item.c_str(), "DUMP") == 0) return dump; if (strcasecmp(item.c_str(), "LOG") == 0) return log; + if (strcasecmp(item.c_str(), "RAW") == 0) return raw; + if (strcasecmp(item.c_str(), "DUMP") == 0) return dump; if (strcasecmp(item.c_str(), "RELOAD") == 0) return reload; if (strcasecmp(item.c_str(), "HELP") == 0) return help; diff --git a/src/ebusd/ebusloop.cpp b/src/ebusd/ebusloop.cpp index 6832d7b7..79f0d778 100644 --- a/src/ebusd/ebusloop.cpp +++ b/src/ebusd/ebusloop.cpp @@ -24,207 +24,520 @@ extern LogInstance& L; extern Appl& A; -EBusLoop::EBusLoop(Commands* commands) : m_commands(commands), m_stop(false) +EBusLoop::EBusLoop(Commands* commands) + : m_commands(commands), m_stop(false), m_lockCounter(0), m_priorRetry(false) { - m_deviceName = A.getParam("p_device"); + m_port = new Port(A.getParam("p_device"), A.getParam("p_nodevicecheck")); + m_port->open(); - m_bus = new Bus(m_deviceName, - A.getParam("p_nodevicecheck"), - A.getParam("p_recvtimeout"), - A.getParam("p_dumpfile"), - A.getParam("p_dumpsize"), - A.getParam("p_dump")); + if (m_port->isOpen() == false) + L.log(bus, error, "can't open %s", A.getParam("p_device")); - m_retries = A.getParam("p_retries"); + m_dump = new Dump(A.getParam("p_dumpfile"), A.getParam("p_dumpsize")); + m_dumpState = A.getParam("p_dump"); - m_lookbusretries = A.getParam("p_lookbusretries"); + m_logRawData = A.getParam("p_lograwdata"); m_pollInterval = A.getParam("p_pollinterval"); - m_logAutoSyn = A.getParam("p_logautosyn"); + m_recvTimeout = A.getParam("p_recvtimeout"); - m_bus->connect(); + m_sendRetries = A.getParam("p_sendretries"); - if (m_bus->isConnected() == false) - L.log(bus, error, "can't open %s", m_deviceName.c_str()); + m_lockRetries = A.getParam("p_lockretries"); } EBusLoop::~EBusLoop() { - m_bus->disconnect(); + if (m_port->isOpen() == true) + m_port->close(); - if (m_bus->isConnected() == true) - L.log(bus, error, "error during disconnect."); - - delete m_bus; + delete m_port; + delete m_dump; } void* EBusLoop::run() { - int busResult; - int retries = 0; - int lookbusretries = 0; - bool busCommandActive = false; + int sendRetries = 0; + int lockRetries = 0; // polling time_t pollStart, pollEnd; time(&pollStart); - double pollDelta = 0.0; + double pollDelta; for (;;) { - if (m_bus->isConnected() == true) { + if (m_port->isOpen() == true) { + ssize_t numBytes; - // work on bus - busResult = m_bus->proceed(); - - // new cyc message arrived - if (busResult == RESULT_SYN || busResult == RESULT_BUS_LOCKED) { - SymbolString data = m_bus->getCycData(); - - if (data.size() == 0 && m_logAutoSyn == true) - L.log(bus, trace, "aa"); - - if (data.size() != 0) { - L.log(bus, trace, "%s", data.getDataStr().c_str()); - - int index = m_commands->storeCycData(data.getDataStr()); - - if (index == -1) { - L.log(bus, debug, " command not found"); - - } else if (index == -2) { - L.log(bus, debug, " no commands defined"); - - } else if (index == -3) { - L.log(bus, debug, " search skipped - string too short"); - - } else { - std::string tmp; - tmp += (*m_commands)[index][1]; - tmp += " "; - tmp += (*m_commands)[index][2]; - L.log(bus, event, " cycle [%d] %s", index, tmp.c_str()); - } - } - - if (busResult == RESULT_BUS_LOCKED) - L.log(bus, trace, "bus locked"); - } - - // add new bus command to send - if (busResult == RESULT_SYN && busCommandActive == false && m_sendBuffer.size() != 0) { - BusCommand* busCommand = m_sendBuffer.remove(); - L.log(bus, debug, " msg: %s", busCommand->getCommand().getDataStr().c_str()); - m_bus->addCommand(busCommand); - L.log(bus, debug, " addCommand success"); - busCommandActive = true; - } - - // add new polling command + // add poll command if (m_commands->sizePolDB() > 0) { // check polling delta time(&pollEnd); pollDelta = difftime(pollEnd, pollStart); // add new polling command to send - if (busResult == RESULT_SYN && busCommandActive == false && pollDelta >= m_pollInterval) { - L.log(bus, trace, "polling Intervall reached"); - - int index = m_commands->nextPolCommand(); - if (index < 0) { - L.log(bus, error, "polling index out of range"); - time(&pollStart); - continue; - } - - std::string tmp; - tmp += (*m_commands)[index][1]; - tmp += " "; - tmp += (*m_commands)[index][2]; - L.log(bus, event, " polling [%d] %s", index, tmp.c_str()); - - std::string ebusCommand(A.getParam("p_address")); - ebusCommand += m_commands->getEbusCommand(index); - std::transform(ebusCommand.begin(), ebusCommand.end(), ebusCommand.begin(), tolower); - - BusCommand* busCommand = new BusCommand(ebusCommand, true); - L.log(bus, trace, " msg: %s", ebusCommand.c_str()); - - m_bus->addCommand(busCommand); - L.log(bus, debug, " addCommand success"); - busCommandActive = true; - + if (pollDelta >= m_pollInterval) { + addPollCommand(); time(&pollStart); } - } - // send bus command - if (busResult == RESULT_BUS_ACQUIRED && busCommandActive == true) { - L.log(bus, trace, " getBus success"); - lookbusretries = 0; - BusCommand* busCommand = m_bus->sendCommand(); - L.log(bus, trace, " %s", busCommand->getMessageStr().c_str()); + // read device - no timeout needed (AUTO-SYN) + numBytes = m_port->recv(0); - if (busCommand->isErrorResult() == true && retries < m_retries) { - retries++; - L.log(bus, trace, " retry number: %d", retries); - busCommand->setResult(std::string(), RESULT_OK); - m_bus->addCommand(busCommand); - } else { - retries = 0; - if (busCommand->isPoll() == true) { - // only save correct results - if (busCommand->isErrorResult() == false) + if (numBytes < 0) { + L.log(bus, error, " ERR_DEVICE: generic device error"); + continue; + } + + // cycle bytes + collectCycData(numBytes); + + // send command + if (m_sstr.size() == 0 && m_lockCounter == 0 && m_sendBuffer.size() > 0) { + // acquire Bus + int busResult = acquireBus(); + + // send bus command + if (busResult == RESULT_BUS_ACQUIRED) { + BusCommand* busCommand = sendCommand(); + L.log(bus, trace, " %s", busCommand->getMessageStr().c_str()); + + if (busCommand->isErrorResult() == true) { + if (sendRetries < m_sendRetries) { + sendRetries++; + L.log(bus, trace, " send retry %d", sendRetries); + busCommand->setResult(std::string(), RESULT_OK); + } + else { + sendRetries = 0; + if (busCommand->isPoll() == true) + delete m_sendBuffer.remove(); + else + busCommand->sendSignal(); + } + } + else { + sendRetries = 0; + if (busCommand->isPoll() == true) { m_commands->storePolData(busCommand->getMessageStr().c_str()); // TODO use getResult() - - delete busCommand; - } else { - busCommand->sendSignal(); + delete busCommand; + } + else + busCommand->sendSignal(); } - busCommandActive = false; + lockRetries = 0; + m_lockCounter = A.getParam("p_lockcounter"); } - } + else if (busResult == RESULT_ERR_BUS_LOST) { + L.log(bus, trace, " acquire bus failed"); - // get bus retry - if (busResult == RESULT_BUS_PRIOR_RETRY) - L.log(bus, trace, " getBus prior retry"); + if (lockRetries >= m_lockRetries) { + L.log(bus, event, " lock bus failed"); + BusCommand* busCommand = m_sendBuffer.remove(); + if (busCommand->isPoll() == true) + delete busCommand; + else + busCommand->sendSignal(); - if (busResult == RESULT_ERR_BUS_LOST) { - L.log(bus, trace, " getBus failure"); - if (lookbusretries >= m_lookbusretries) { - L.log(bus, event, " getBus failed - command deleted"); - BusCommand* busCommand = m_bus->delCommand(); - if (busCommand->isPoll() == true) { - delete busCommand; - } else { - busCommand->sendSignal(); + lockRetries = 0; } - lookbusretries = 0; - busCommandActive = false; - }else { - lookbusretries++; + else { + lockRetries++; + L.log(bus, trace, " lock retry %d", lockRetries); + } + + m_lockCounter = A.getParam("p_lockcounter"); } + } - if (busResult == RESULT_ERR_SEND) - L.log(bus, event, " getBus send error"); - - } else { + } + else { + // TODO: define max reopen sleep(10); - m_bus->connect(); + m_port->open(); + + if (m_port->isOpen() == false) + L.log(bus, error, "can't open %s", A.getParam("p_device")); - if (m_bus->isConnected() == false) - L.log(bus, error, "can't open %s", m_deviceName.c_str()); } if (m_stop == true) { - m_bus->disconnect(); + if (m_port->isOpen() == true) + m_port->close(); + return NULL; } + } return NULL; } +unsigned char EBusLoop::fetchByte() +{ + unsigned char byte; + + // fetch byte + byte = m_port->byte(); + + if (m_dumpState == true) + m_dump->write((const char*) &byte); + + if (m_logRawData == true) + L.log(bus, event, "%02x", byte); + + return byte; +} + +void EBusLoop::collectCycData(const int numRecv) +{ + // cycle bytes + for (int i = 0; i < numRecv; i++) { + + // fetch byte + unsigned char byte = fetchByte(); + + if (byte == SYN) { + + // analyse cycle data + if (m_sstr.size() > 0) { + + analyseCycData(); + + if (m_sstr.size() == 1 && m_lockCounter == 0 && m_priorRetry == false) + m_lockCounter++; + + else if (m_lockCounter > 0) + m_lockCounter--; + + m_sstr.clear(); + } + + else if (m_lockCounter > 0) + m_lockCounter--; + + } + + // collect cycle data + else + m_sstr.push_back(byte, true, false); + } +} + +void EBusLoop::analyseCycData() +{ + L.log(bus, trace, "%s", m_sstr.getDataStr().c_str()); + + int index = m_commands->storeCycData(m_sstr.getDataStr()); + + if (index == -1) { + L.log(bus, debug, " command not found"); + } + else if (index == -2) { + L.log(bus, debug, " no commands defined"); + } + else if (index == -3) { + L.log(bus, debug, " search skipped - string too short"); + } + else { + std::string tmp; + tmp += (*m_commands)[index][1]; + tmp += " "; + tmp += (*m_commands)[index][2]; + L.log(bus, event, " cycle [%4d] %s", index, tmp.c_str()); + } +} + +void EBusLoop::addPollCommand() +{ + int index = m_commands->nextPolCommand(); + if (index < 0) { + L.log(bus, error, "polling index out of range"); + } + else { + // TODO: implement as methode from class commands? + std::string tmp; + tmp += (*m_commands)[index][1]; + tmp += " "; + tmp += (*m_commands)[index][2]; + L.log(bus, event, " polling [%4d] %s", index, tmp.c_str()); + + std::string ebusCommand(A.getParam("p_address")); + ebusCommand += m_commands->getEbusCommand(index, false); + std::transform(ebusCommand.begin(), ebusCommand.end(), ebusCommand.begin(), tolower); + + BusCommand* busCommand = new BusCommand(ebusCommand, true); + L.log(bus, trace, " msg: %s", ebusCommand.c_str()); + + addBusCommand(busCommand); + } +} + +int EBusLoop::acquireBus() +{ + unsigned char recvByte, sendByte; + ssize_t numRecv, numSend; + + sendByte = m_sendBuffer.next()->getCommand()[0]; + + // send QQ + numSend = m_port->send(&sendByte); + if (numSend <= 0) { + L.log(bus, error, " ERR_SEND: send error"); + return RESULT_ERR_SEND; + } + + // receive 1 byte - must be QQ + numRecv = m_port->recv(0); + + if (numRecv < 0) { + L.log(bus, error, " ERR_DEVICE: generic device error"); + return RESULT_ERR_DEVICE; + } + + if (numRecv == 1) { + // fetch byte + recvByte = fetchByte(); + + // compare sent and received byte + if (sendByte == recvByte) { + L.log(bus, trace, " bus acquired"); + return RESULT_BUS_ACQUIRED; + } + + // collect cycle data + if (recvByte != SYN) + m_sstr.push_back(recvByte, true, false); + + // compare prior nibble for retry + if ((sendByte & 0x0F) == (recvByte & 0x0F)) { + m_priorRetry = true; + L.log(bus, trace, " bus prior retry"); + return RESULT_BUS_PRIOR_RETRY; + } + + L.log(bus, error, " ERR_BUS_LOST: lost bus arbitration"); + return RESULT_ERR_BUS_LOST; + } + + // cycle bytes + collectCycData(numRecv); + + L.log(bus, error, " ERR_EXTRA_DATA: received bytes > sent bytes"); + return RESULT_ERR_EXTRA_DATA; +} + +BusCommand* EBusLoop::sendCommand() +{ + unsigned char recvByte; + std::string result; + SymbolString slaveData; + int retval = RESULT_OK; + + BusCommand* busCommand = m_sendBuffer.next(); + + // send ZZ PB SB NN Dx CRC + SymbolString command = busCommand->getCommand(); + for (size_t i = 1; i < command.size(); i++) { + retval = sendByte(command[i]); + if (retval < 0) + goto on_exit; + } + + // BC -> send SYN + if (busCommand->getType() == broadcast) { + sendByte(SYN); + goto on_exit; + } + + // receive ACK + retval = recvSlaveAck(recvByte); + if (retval < 0) + goto on_exit; + + // is slave ACK negative? + if (recvByte == NAK) { + + // send QQ ZZ PB SB NN Dx CRC again + for (size_t i = 0; i < command.size(); i++) { + retval = sendByte(command[i]); + if (retval < 0) + goto on_exit; + } + + // receive ACK + retval = recvSlaveAck(recvByte); + if (retval < 0) + goto on_exit; + + // is slave ACK negative? + if (recvByte == NAK) { + sendByte(SYN); + L.log(bus, error, " ERR_NAK: NAK received"); + retval = RESULT_ERR_NAK; + goto on_exit; + } + } + + // MM -> send SYN + if (busCommand->getType() == masterMaster) { + sendByte(SYN); + goto on_exit; + } + + // receive NN, Dx, CRC + retval = recvSlaveData(slaveData); + + // are calculated and received CRC equal? + if (retval == RESULT_ERR_CRC) { + + // send NAK + retval = sendByte(NAK); + if (retval < 0) + goto on_exit; + + // receive NN, Dx, CRC + slaveData.clear(); + retval = recvSlaveData(slaveData); + + // are calculated and received CRC equal? + if (retval == RESULT_ERR_CRC) { + + // send NAK + retval = sendByte(NAK); + if (retval >= 0) + retval = RESULT_ERR_CRC; + } + } + + if (retval < 0) + goto on_exit; + + // send ACK + retval = sendByte(ACK); + if (retval == -1) { + L.log(bus, error, " ERR_ACK: ACK error"); + retval = RESULT_ERR_ACK; + goto on_exit; + } + + // MS -> send SYN + sendByte(SYN); + +on_exit: + + // empty receive buffer + while (m_port->size() != 0) + recvByte = fetchByte(); + + busCommand->setResult(slaveData, retval); + + if (retval == RESULT_OK) + return m_sendBuffer.remove(); + else + return busCommand; + +} + +int EBusLoop::sendByte(const unsigned char sendByte) +{ + unsigned char recvByte; + ssize_t numRecv, numSend; + + numSend = m_port->send(&sendByte); + + // receive 1 byte - must be equal + numRecv = m_port->recv(RECV_TIMEOUT); + + if (numSend != numRecv) { + L.log(bus, error, " ERR_EXTRA_DATA: received bytes > sent bytes"); + return RESULT_ERR_EXTRA_DATA; + } + + recvByte = fetchByte(); + + if (sendByte != recvByte) { + L.log(bus, error, " ERR_SEND: send error"); + return RESULT_ERR_SEND; + } + + return RESULT_OK; +} + +int EBusLoop::recvSlaveAck(unsigned char& recvByte) +{ + ssize_t numRecv; + + // receive ACK + numRecv = m_port->recv(m_recvTimeout); + + if (numRecv > 1) { + L.log(bus, error, " ERR_EXTRA_DATA: received bytes > sent bytes"); + return RESULT_ERR_EXTRA_DATA; + } + else if (numRecv < 0) { + L.log(bus, error, " ERR_TIMEOUT: read timeout"); + return RESULT_ERR_TIMEOUT; + } + + recvByte = fetchByte(); + + // is received byte SYN? + if (recvByte == SYN) { + L.log(bus, error, " ERR_SYN: SYN received"); + return RESULT_ERR_SYN; + } + + return RESULT_OK; +} + +int EBusLoop::recvSlaveData(SymbolString& result) +{ + unsigned char recvByte, calcCrc = 0; + ssize_t numRecv; + size_t NN = 0; + bool updateCrc = true; + int retval = 0; + + for (size_t i = 0, needed = 1; i < needed; i++) { + numRecv = m_port->recv(RECV_TIMEOUT); + if (numRecv < 0) { + L.log(bus, error, " ERR_TIMEOUT: read timeout"); + return RESULT_ERR_TIMEOUT; + } + + recvByte = fetchByte(); + retval = result.push_back(recvByte, true, updateCrc); + if (retval < 0) + return retval; + + if (retval == RESULT_IN_ESC) + needed++; + else if (result.size() == 1) { // NN received + NN = result[0]; + needed += NN; + } + else if (NN > 0 && result.size() == 1+NN) {// all data received + updateCrc = false; + calcCrc = result.getCRC(); + needed++; + } + } + + if (retval == RESULT_IN_ESC) { + L.log(bus, error, " ERR_ESC: invalid escape sequence received"); + return RESULT_ERR_ESC; + } + + if (updateCrc == true || calcCrc != result[result.size()-1]) { + L.log(bus, error, " ERR_CRC: CRC error"); + return RESULT_ERR_CRC; + } + + return RESULT_OK; +} + diff --git a/src/ebusd/ebusloop.h b/src/ebusd/ebusloop.h index 09c69992..1605451e 100644 --- a/src/ebusd/ebusloop.h +++ b/src/ebusd/ebusloop.h @@ -20,11 +20,16 @@ #ifndef EBUSLOOP_H_ #define EBUSLOOP_H_ -#include "bus.h" #include "commands.h" +#include "port.h" +#include "dump.h" +#include "buscommand.h" #include "wqueue.h" #include "thread.h" +/** the maximum time [us] allowed for retrieving a byte from an addressed slave */ +#define RECV_TIMEOUT 10000 + using namespace libebus; @@ -40,20 +45,42 @@ public: void addBusCommand(BusCommand* busCommand) { m_sendBuffer.add(busCommand); } - void dump(const bool dumpState) { m_bus->setDumpState(dumpState); } + void dump() { m_dumpState == true ? m_dumpState = false : m_dumpState = true ; } + void raw() { m_logRawData == true ? m_logRawData = false : m_logRawData = true ; } void newCommands(Commands* commands) { m_commands = commands; } private: Commands* m_commands; - std::string m_deviceName; - Bus* m_bus; + Port* m_port; + + Dump* m_dump; + bool m_dumpState; + + bool m_logRawData; + bool m_stop; + + int m_lockCounter; + bool m_priorRetry; + WQueue m_sendBuffer; - int m_retries; - int m_lookbusretries; + SymbolString m_sstr; + double m_pollInterval; - bool m_logAutoSyn; + long m_recvTimeout; + int m_sendRetries; + int m_lockRetries; + + unsigned char fetchByte(); + void collectCycData(const int numRecv); + void analyseCycData(); + void addPollCommand(); + int acquireBus(); + BusCommand* sendCommand(); + int sendByte(const unsigned char sendByte); + int recvSlaveAck(unsigned char& recvByte); + int recvSlaveData(SymbolString& result); }; diff --git a/src/ebusd/main.cpp b/src/ebusd/main.cpp index 015eee56..459c5579 100644 --- a/src/ebusd/main.cpp +++ b/src/ebusd/main.cpp @@ -47,12 +47,16 @@ void define_args() "disable valid ebus device test\n", Appl::type_bool, Appl::opt_none); - A.addItem("p_retries", Appl::Param(2), "r", "retries", - "\tnumber retries send ebus command (2)", + A.addItem("p_sendretries", Appl::Param(2), "s", "sendretries", + "number retries send ebus command (2)", Appl::type_int, Appl::opt_mandatory); - A.addItem("p_lookbusretries", Appl::Param(2), "", "lookbusretries", - "number retries to look ebus (2)", + A.addItem("p_lockretries", Appl::Param(2), "", "lockretries", + "number retries to lock ebus (2)", + Appl::type_int, Appl::opt_mandatory); + + A.addItem("p_lockcounter", Appl::Param(5), "", "lockcounter", + "number of SYN to unlock send function (5)", Appl::type_int, Appl::opt_mandatory); A.addItem("p_recvtimeout", Appl::Param(15000), "", "recvtimeout", @@ -91,8 +95,8 @@ void define_args() "\tlog level - error|event|trace|debug (event)", Appl::type_string, Appl::opt_mandatory); - A.addItem("p_logautosyn", Appl::Param(false), "", "logautosyn", - "log AUTO-SYN bytes\n", + A.addItem("p_lograwdata", Appl::Param(false), "", "lograwdata", + "log raw data (bytes)\n", Appl::type_bool, Appl::opt_none); A.addItem("p_dump", Appl::Param(false), "D", "dump", diff --git a/src/libebus/Makefile.am b/src/lib/ebus/Makefile.am similarity index 94% rename from src/libebus/Makefile.am rename to src/lib/ebus/Makefile.am index e78d40bc..64fa53d9 100644 --- a/src/libebus/Makefile.am +++ b/src/lib/ebus/Makefile.am @@ -14,8 +14,6 @@ libebus_a_SOURCES = result.cpp \ port.h \ buscommand.cpp \ buscommand.h \ - bus.cpp \ - bus.h \ command.cpp \ command.h \ commands.cpp \ diff --git a/src/libebus/buscommand.cpp b/src/lib/ebus/buscommand.cpp similarity index 93% rename from src/libebus/buscommand.cpp rename to src/lib/ebus/buscommand.cpp index 14a3b60d..ac822f63 100644 --- a/src/libebus/buscommand.cpp +++ b/src/lib/ebus/buscommand.cpp @@ -22,7 +22,6 @@ namespace libebus { - BusCommand::BusCommand(const std::string commandStr, const bool isPoll) : m_isPoll(isPoll), m_command(commandStr), m_result(), m_resultCode(RESULT_OK) { @@ -34,6 +33,7 @@ BusCommand::BusCommand(const std::string commandStr, const bool isPoll) m_type = masterMaster; else m_type = masterSlave; + pthread_mutex_init(&m_mutex, NULL); pthread_cond_init(&m_cond, NULL); } @@ -44,11 +44,6 @@ BusCommand::~BusCommand() pthread_cond_destroy(&m_cond); } -const char* BusCommand::getResultCodeCStr() -{ - return libebus::getResultCodeCStr(m_resultCode); -} - const std::string BusCommand::getMessageStr() { std::string result; @@ -59,9 +54,9 @@ const std::string BusCommand::getMessageStr() result += "00"; result += m_result.getDataStr(); result += "00"; - } else { - result = "success"; } + else + result = "success"; } else result = "error: "+std::string(getResultCodeCStr()); diff --git a/src/libebus/buscommand.h b/src/lib/ebus/buscommand.h similarity index 88% rename from src/libebus/buscommand.h rename to src/lib/ebus/buscommand.h index b469ae3c..bf06e37d 100644 --- a/src/libebus/buscommand.h +++ b/src/lib/ebus/buscommand.h @@ -34,17 +34,22 @@ class BusCommand { public: - BusCommand(const std::string commandStr, const bool isPoll); + BusCommand(const std::string command, const bool isPoll); ~BusCommand(); CommandType getType() const { return m_type; } bool isPoll() const { return m_isPoll; } + SymbolString getCommand() const { return m_command; } - bool isErrorResult() const { return m_resultCode < 0; } - const char* getResultCodeCStr(); SymbolString getResult() const { return m_result; } - void setResult(const SymbolString result, const int resultCode) { m_result = result; m_resultCode = resultCode; } + + bool isErrorResult() const { return m_resultCode < 0; } + const char* getResultCodeCStr() const { return libebus::getResultCodeCStr(m_resultCode); } + void setResult(const SymbolString result, const int resultCode) + { m_result = result; m_resultCode = resultCode; } + const std::string getMessageStr(); + void waitSignal() { pthread_cond_wait(&m_cond, &m_mutex); } // TODO timeout void sendSignal() { pthread_cond_signal(&m_cond); } diff --git a/src/libebus/command.cpp b/src/lib/ebus/command.cpp similarity index 100% rename from src/libebus/command.cpp rename to src/lib/ebus/command.cpp diff --git a/src/libebus/command.h b/src/lib/ebus/command.h similarity index 100% rename from src/libebus/command.h rename to src/lib/ebus/command.h diff --git a/src/libebus/commands.cpp b/src/lib/ebus/commands.cpp similarity index 93% rename from src/libebus/commands.cpp rename to src/lib/ebus/commands.cpp index 97146ce2..cee9ad91 100644 --- a/src/libebus/commands.cpp +++ b/src/lib/ebus/commands.cpp @@ -127,15 +127,20 @@ int Commands::findCommand(const std::string& data) const return -1; } -std::string Commands::getEbusCommand(const int index) const +std::string Commands::getEbusCommand(const int index, const bool cycle) const { cmd_t command = m_cmdDB.at(index); - std::string cmd(command[5]); - cmd += command[6]; + std::string cmd; std::stringstream sstr; + + if (cycle == true) + cmd += command[4]; // QQ + + cmd += command[5]; // ZZ + cmd += command[6]; // PBSB sstr << std::setw(2) << std::hex << std::setfill('0') << command[7]; - cmd += sstr.str(); - cmd += command[8]; + cmd += sstr.str(); // NN + cmd += command[8]; // Dx return cmd; } @@ -158,7 +163,7 @@ int Commands::storeCycData(const std::string& data) const // walk through commands for (; iter != m_cycDB.end(); iter++) { - std::string command = getEbusCommand(iter->first); + std::string command = getEbusCommand(iter->first, true); // skip wrong search string length if (command.length() > search.length()) @@ -211,7 +216,7 @@ void Commands::storePolData(const std::string& data) const // walk through commands for (; iter != m_polDB.end(); iter++) { - std::string command = getEbusCommand(iter->first); + std::string command = getEbusCommand(iter->first, false); // skip wrong search string length if (command.length() > search.length()) diff --git a/src/libebus/commands.h b/src/lib/ebus/commands.h similarity index 96% rename from src/libebus/commands.h rename to src/lib/ebus/commands.h index 121587a0..09c96a89 100644 --- a/src/libebus/commands.h +++ b/src/lib/ebus/commands.h @@ -56,7 +56,7 @@ public: std::string getCmdType(const int index) const { return std::string(m_cmdDB.at(index)[0]); } std::string getEbusType(const int index) const { return std::string(m_cmdDB.at(index)[4]); } - std::string getEbusCommand(const int index) const; + std::string getEbusCommand(const int index, const bool cycle) const; int storeCycData(const std::string& data) const; std::string getCycData(int index) const; diff --git a/src/libebus/configfile.cpp b/src/lib/ebus/configfile.cpp similarity index 93% rename from src/libebus/configfile.cpp rename to src/lib/ebus/configfile.cpp index 70e42917..0520580c 100644 --- a/src/libebus/configfile.cpp +++ b/src/lib/ebus/configfile.cpp @@ -26,7 +26,7 @@ namespace libebus { -void ConfigFileCSV::readFile(std::istream& is, Commands& commands) +void ConfigFileCSV::parse(std::istream& is, Commands& commands) { std::string line; @@ -50,9 +50,9 @@ void ConfigFileCSV::readFile(std::istream& is, Commands& commands) }; -void ConfigFileXML::readFile(std::istream& is, Commands& commands) +void ConfigFileXML::parse(std::istream& is, Commands& commands) { - ; // ToDo: Implamantion for xml files + ; // ToDo: Implementation for xml files } @@ -91,7 +91,7 @@ Commands* ConfigCommands::getCommands() std::fstream file((*i).c_str(), std::ios::in); if(file.is_open() == true) { - m_configfile->readFile(file, *commands); + m_configfile->parse(file, *commands); file.close(); } } diff --git a/src/lib/ebus/configfile.h b/src/lib/ebus/configfile.h new file mode 100644 index 00000000..4d5183b1 --- /dev/null +++ b/src/lib/ebus/configfile.h @@ -0,0 +1,150 @@ +/* + * Copyright (C) Roland Jax 2012-2014 + * + * This file is part of ebusd. + * + * ebusd 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 3 of the License, or + * (at your option) any later version. + * + * ebusd is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with ebusd. If not, see http://www.gnu.org/licenses/. + */ + +#ifndef LIBEBUS_CONFIGFILE_H_ +#define LIBEBUS_CONFIGFILE_H_ + +#include "commands.h" +#include +#include + +namespace libebus +{ + +/** available file endings / types. */ +enum FileType { CSV, XML }; + +/** + * @brief Base class for config files. + */ +class ConfigFile +{ + +public: + /** + * @brief Destructor. + */ + virtual ~ConfigFile() {} + + /** + * @brief read input stream and stored data into commands + * @param is open input stream for reading. + * @param commands object as datastore. + */ + virtual void parse(std::istream& is, Commands& commands) = 0; + +}; + +/** + * @brief Class for CSV config files. + */ +class ConfigFileCSV : public ConfigFile +{ + +public: + /** + * @brief Destructor. + */ + ~ConfigFileCSV() {} + + /** + * @brief read input stream and stored data into commands + * @param is open input stream for reading. + * @param commands object as datastore. + */ + void parse(std::istream& is, Commands& commands); + +}; + +/** + * @brief Class for XML config files. + */ +class ConfigFileXML : public ConfigFile +{ + +public: + /** + * @brief Destructor. + */ + ~ConfigFileXML() {} + + /** + * @brief read input stream and stored data into commands + * @param is open input stream for reading. + * @param commands object as datastore. + */ + void parse(std::istream& is, Commands& commands); + +}; + + +/** + * @brief Class for class Device. + */ +class ConfigCommands +{ + +public: + /** + * @brief Set file type and add recursive files from given path. + * @param path to configuration files. + * @param Filetype to parse. + */ + ConfigCommands(const std::string path, const FileType type); + + /** + * @brief Destructor. + */ + ~ConfigCommands() { delete m_configfile; } + + /** + * @brief setter for file type. + * @param FileType of files. + */ + void setType(const FileType type); + + /** + * @brief Parse files for commands and store them into commands instance. + * @return a commands instance + */ + Commands* getCommands(); + +private: + /** the configfile instance */ + ConfigFile* m_configfile; + /** main path for configuration files */ + std::string m_path; + /** valid file extension */ + std::string m_extension; + /** vector of configuration files */ + std::vector m_files; + + /** + * @brief parse path for given file extension. + * @param path to configuration files. + * @param extension with file type. + */ + void addFiles(const std::string path, const std::string extension); + +}; + + +} //namespace + +#endif // LIBEBUS_CONFIGFILE_H_ diff --git a/src/libebus/data.cpp b/src/lib/ebus/data.cpp similarity index 100% rename from src/libebus/data.cpp rename to src/lib/ebus/data.cpp diff --git a/src/libebus/data.h b/src/lib/ebus/data.h similarity index 100% rename from src/libebus/data.h rename to src/lib/ebus/data.h diff --git a/src/libebus/decode.cpp b/src/lib/ebus/decode.cpp similarity index 100% rename from src/libebus/decode.cpp rename to src/lib/ebus/decode.cpp diff --git a/src/libebus/decode.h b/src/lib/ebus/decode.h similarity index 100% rename from src/libebus/decode.h rename to src/lib/ebus/decode.h diff --git a/src/libebus/dump.cpp b/src/lib/ebus/dump.cpp similarity index 100% rename from src/libebus/dump.cpp rename to src/lib/ebus/dump.cpp diff --git a/src/libebus/dump.h b/src/lib/ebus/dump.h similarity index 63% rename from src/libebus/dump.h rename to src/lib/ebus/dump.h index 2062104a..34418139 100644 --- a/src/libebus/dump.h +++ b/src/lib/ebus/dump.h @@ -25,21 +25,44 @@ namespace libebus { - +/** + * @brief Class for writing raw bytes to binary file. + */ class Dump { public: + /** + * @brief Create a new instance to write dump files. + * @param filename which will be used for dumping raw bytes. + * @param filesize max. Size of the dump file, before switching. + */ Dump(std::string filename, long filesize) : m_filename(filename), m_filesize(filesize) {} + /** + * @brief write byte to dump file. + * @param byte to write + * @return -1 if dump file cannot opened or renaming of dump file failed. + */ int write(const char* byte); + /** + * @brief setter for dump file name. + * @param filename which will be used for dumping raw bytes. + */ void setFilename(const std::string& filename) { m_filename = filename; } + + /** + * @brief setter for max size of dump file. + * @param filesize max. Size of the dump file, before switching. + */ void setFilesize(const long filesize) { m_filesize = filesize; } private: + /** the name of dump file*/ std::string m_filename; + /** max. size of dump file */ long m_filesize; }; diff --git a/src/libebus/encode.cpp b/src/lib/ebus/encode.cpp similarity index 100% rename from src/libebus/encode.cpp rename to src/lib/ebus/encode.cpp diff --git a/src/libebus/encode.h b/src/lib/ebus/encode.h similarity index 100% rename from src/libebus/encode.h rename to src/lib/ebus/encode.h diff --git a/src/libebus/port.cpp b/src/lib/ebus/port.cpp similarity index 96% rename from src/libebus/port.cpp rename to src/lib/ebus/port.cpp index 8b1dd1c8..c815182b 100644 --- a/src/libebus/port.cpp +++ b/src/lib/ebus/port.cpp @@ -60,7 +60,7 @@ bool Device::isValid() ssize_t Device::sendBytes(const unsigned char* buffer, size_t nbytes) { if (isValid() == false) - return -1; + return -1; // TODO RESULT_ERR_DEVICE // write bytes to device return write(m_fd, buffer, nbytes); @@ -86,18 +86,16 @@ ssize_t Device::recvBytes(const long timeout, size_t maxCount) return -2; // TODO RESULT_ERR_TIMEOUT } - ssize_t bytes_read = sizeof(m_buffer); if (maxCount > sizeof(m_buffer)) maxCount = sizeof(m_buffer); - // read bytes from device - bytes_read = read(m_fd, m_buffer, maxCount); + ssize_t nbytes = read(m_fd, m_buffer, maxCount); - for (int i = 0; i < bytes_read; i++) + for (int i = 0; i < nbytes; i++) m_recvBuffer.push(m_buffer[i]); - return bytes_read; + return nbytes; } unsigned char Device::getByte() diff --git a/src/lib/ebus/port.h b/src/lib/ebus/port.h new file mode 100644 index 00000000..7dc8e53a --- /dev/null +++ b/src/lib/ebus/port.h @@ -0,0 +1,267 @@ +/* + * Copyright (C) Roland Jax 2012-2014 + * + * This file is part of ebusd. + * + * ebusd 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 3 of the License, or + * (at your option) any later version. + * + * ebusd is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with ebusd. If not, see http://www.gnu.org/licenses/. + */ + +#ifndef LIBEBUS_PORT_H_ +#define LIBEBUS_PORT_H_ + +#include +#include +#include +#include + +namespace libebus +{ + +/** available device types. */ +enum DeviceType { SERIAL, NETWORK }; + +/** max bytes write to bus. */ +#define MAX_WRITE_SIZE 1 + +/** max size of receive buffer. */ +#define MAX_READ_SIZE 100 + + +/** + * @brief Base class for input devices. + */ +class Device +{ + +public: + /** + * @brief Constructs a new instance. + */ + Device() : m_fd(-1), m_open(false), m_noDeviceCheck(false) {} + + /** + * @brief Destructor. + */ + virtual ~Device() {} + + /** + * @brief virtual open function for opening file descriptor + * @param deviceName to determine device type. + * @param noDeviceCheck en-/disable device check. + */ + virtual void openDevice(const std::string deviceName, const bool noDeviceCheck) = 0; + + /** + * @brief virtual close function for closing opened file descriptor + */ + virtual void closeDevice() = 0; + + /** + * @brief connection state of device. + * @return true if device is open + */ + bool isOpen(); + + /** + * @brief sendBytes write bytes into opened file descriptor. + * @param buffer data to send. + * @param nbytes number of bytes to send. + * @return number of written bytes or -1 if an error has occured. + */ + ssize_t sendBytes(const unsigned char* buffer, size_t nbytes); + + /** + * @brief recvBytes read bytes from opened file descriptor. + * @param timeout max time out for new input data. + * @param maxCount max size of receive buffer. + * @return number of read bytes or -1 if an error has occured. + */ + ssize_t recvBytes(const long timeout, size_t maxCount); + + /** + * @brief fetch first byte from receive buffer. + * @return first byte (raw) + */ + unsigned char getByte(); + + /** + * @brief get current size (bytes) of the receive buffer. + * @return number of bytes in queued. + */ + ssize_t sizeRecvBuffer() const { return m_recvBuffer.size(); } + +protected: + /** if of file descriptor */ + int m_fd; + /** state of device*/ + bool m_open; + /** state of device check */ + bool m_noDeviceCheck; + /** queue for received bytes */ + std::queue m_recvBuffer; + /** receive buffer */ + unsigned char m_buffer[MAX_READ_SIZE]; + +private: + /** + * @brief system check if opened file descriptor is valid + * @return true if file descriptor is valid + */ + bool isValid(); + +}; + +/** + * @brief Class for serial input device. + */ +class DeviceSerial : public Device +{ + +public: + /** + * @brief Destructor. + */ + ~DeviceSerial() { closeDevice(); } + + /** + * @brief open function for opening file descriptor + * @param deviceName to determine device type. + * @param noDeviceCheck en-/disable device check. + */ + void openDevice(const std::string deviceName, const bool noDeviceCheck); + + /** + * @brief close function for closing opened file descriptor + */ + void closeDevice(); + +private: + /** save settings from serial device */ + termios m_oldSettings; + +}; + +/** + * @brief Class for network input device. + */ +class DeviceNetwork : public Device +{ + +public: + /** + * @brief Destructor. + */ + ~DeviceNetwork() { closeDevice(); } + + /** + * @brief open function for opening file descriptor + * @param deviceName to determine device type. + * @param noDeviceCheck en-/disable device check. + */ + void openDevice(const std::string deviceName, const bool noDeviceCheck); + + /** + * @brief close opened file descriptor + */ + void closeDevice(); + +private: + +}; + +/** + * @brief Wrapper class for class Device. + */ +class Port +{ + +public: + /** + * @brief Constructs a new instance and determine device type. + * @param deviceName to determine device type. + * @param noDeviceCheck en-/disable device check. + */ + Port(const std::string deviceName, const bool noDeviceCheck); + + /** + * @brief Destructor. + */ + ~Port() { delete m_device; } + + /** + * @brief open device + */ + void open() { m_device->openDevice(m_deviceName, m_noDeviceCheck); } + + /** + * @brief close device + */ + void close() { m_device->closeDevice(); } + + /** + * @brief connection state of device. + * @return true if device is open + */ + bool isOpen() { return m_device->isOpen(); } + + /** + * @brief send write bytes into opened file descriptor. + * @param buffer data to send. + * @param nbytes number of bytes to send. + * @return number of written bytes or -1 if an error has occured. + */ + ssize_t send(const unsigned char* buffer, size_t nbytes = MAX_WRITE_SIZE) + { return m_device->sendBytes(buffer, nbytes); } + + /** + * @brief recv read bytes from opened file descriptor. + * @param timeout max time out for new input data. + * @param maxCount max size of receive buffer. + * @return number of read bytes or -1 if an error has occured. + */ + ssize_t recv(const long timeout, size_t maxCount = MAX_READ_SIZE) + { return m_device->recvBytes(timeout, maxCount); } + + /** + * @brief fetch first byte from receive buffer. + * @return first byte (raw) + */ + unsigned char byte() { return m_device->getByte(); } + + /** + * @brief get current size (bytes) of the receive buffer. + * @return number of bytes in queued. + */ + ssize_t size() const { return m_device->sizeRecvBuffer(); } + +private: + /** the device name */ + std::string m_deviceName; + /** the device instance */ + Device* m_device; + /** true if device check is disabled */ + bool m_noDeviceCheck; + + /** + * @brief internal setter for device type. + * @param type of device + */ + void setType(const DeviceType type); + +}; + + +} //namespace + +#endif // LIBEBUS_PORT_H_ diff --git a/src/libebus/result.cpp b/src/lib/ebus/result.cpp similarity index 96% rename from src/libebus/result.cpp rename to src/lib/ebus/result.cpp index 4374d3d9..ba2f6008 100644 --- a/src/libebus/result.cpp +++ b/src/lib/ebus/result.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) John Baier 2012-2014 + * Copyright (C) John Baier 2014 * * This file is part of ebusd. * diff --git a/src/libebus/result.h b/src/lib/ebus/result.h similarity index 97% rename from src/libebus/result.h rename to src/lib/ebus/result.h index c0f86edf..7a439382 100644 --- a/src/libebus/result.h +++ b/src/lib/ebus/result.h @@ -1,5 +1,5 @@ /* - * Copyright (C) John Baier 2012-2014 + * Copyright (C) John Baier 2014 * * This file is part of ebusd. * diff --git a/src/libebus/symbol.cpp b/src/lib/ebus/symbol.cpp similarity index 96% rename from src/libebus/symbol.cpp rename to src/lib/ebus/symbol.cpp index 287020bf..05d09ab1 100644 --- a/src/libebus/symbol.cpp +++ b/src/lib/ebus/symbol.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) John Baier 2012-2014 + * Copyright (C) John Baier 2014 * * This file is part of ebusd. * @@ -79,15 +79,13 @@ const std::string SymbolString::getDataStr(const bool unescape) for (size_t i = 0; i < m_data.size(); i++) { unsigned char value = m_data[i]; if (m_unescapeState == 0 && unescape == true && previousEscape == true) { - if (value == 0x00) { + if (value == 0x00) sstr << "a9"; // ESC - } - else if (value == 0x01) { + else if (value == 0x01) sstr << "aa"; // SYN - } - else { + else sstr << "XX"; // invalid escape sequence - } + previousEscape = false; } else if (m_unescapeState == 0 && unescape == true && value == ESC) { @@ -123,9 +121,9 @@ int SymbolString::push_back(const unsigned char value, const bool isEscaped, con } else { m_data.push_back(value); - if (updateCRC) { + if (updateCRC) addCRC(value); - } + } return RESULT_OK; } @@ -149,9 +147,9 @@ int SymbolString::push_back(const unsigned char value, const bool isEscaped, con return RESULT_OK; } else if (m_unescapeState != 1) { - if (updateCRC) { + if (updateCRC) addCRC(value); - } + if (value == 0x00) { m_data.push_back(ESC); m_unescapeState = 1; @@ -165,15 +163,15 @@ int SymbolString::push_back(const unsigned char value, const bool isEscaped, con return RESULT_ERR_ESC; // invalid escape sequence } else if (value == ESC) { - if (updateCRC) { + if (updateCRC) addCRC(value); - } + m_unescapeState = 2; return RESULT_IN_ESC; } - if (updateCRC) { + if (updateCRC) addCRC(value); - } + m_data.push_back(value); return RESULT_OK; } diff --git a/src/libebus/symbol.h b/src/lib/ebus/symbol.h similarity index 96% rename from src/libebus/symbol.h rename to src/lib/ebus/symbol.h index 1ea8dad4..c54a1fc8 100644 --- a/src/libebus/symbol.h +++ b/src/lib/ebus/symbol.h @@ -1,5 +1,5 @@ /* - * Copyright (C) John Baier 2012-2014 + * Copyright (C) John Baier 2014 * * This file is part of ebusd. * @@ -41,6 +41,7 @@ static const unsigned char BROADCAST = 0xFE; // the broadcast destination addres */ class SymbolString { + public: /** * @brief Creates a new unescaped empty instance. @@ -81,7 +82,7 @@ public: * @param other the other instance. * @return true if this instance is equal to the other instance (i.e. both escaped or both unescaped and same symbols). */ - bool operator==(SymbolString other) { return m_unescapeState==other.m_unescapeState && m_data==other.m_data; } + bool operator==(SymbolString other) { return (m_unescapeState==0)==(other.m_unescapeState==0) && m_data==other.m_data; } /** * @brief Appends a the symbol to the end of the symbol string and escapes/unescapes it if necessary. * @param value the symbol to append. diff --git a/src/lib/ebus/test/Makefile.am b/src/lib/ebus/test/Makefile.am new file mode 100644 index 00000000..55dff9aa --- /dev/null +++ b/src/lib/ebus/test/Makefile.am @@ -0,0 +1,37 @@ +AM_CXXFLAGS = -fpic \ + -Wall \ + -Wextra \ + -I$(top_srcdir)/src/lib/ebus + +noinst_PROGRAMS = test_port \ + test_symbol \ + test_data \ + test_commands \ + test_configfile \ + test_decode \ + test_encode + +test_port_SOURCES = test_port.cpp +test_port_LDADD = $(top_srcdir)/src/lib/ebus/libebus.a + +test_symbol_SOURCES = test_symbol.cpp +test_symbol_LDADD = $(top_srcdir)/src/lib/ebus/libebus.a + +test_data_SOURCES = test_data.cpp +test_data_LDADD = $(top_srcdir)/src/lib/ebus/libebus.a + +test_commands_SOURCES = test_commands.cpp +test_commands_LDADD = $(top_srcdir)/src/lib/ebus/libebus.a + +test_configfile_SOURCES = test_configfile.cpp +test_configfile_LDADD = $(top_srcdir)/src/lib/ebus/libebus.a + +test_decode_SOURCES = test_decode.cpp +test_decode_LDADD = $(top_srcdir)/src/lib/ebus/libebus.a + +test_encode_SOURCES = test_encode.cpp +test_encode_LDADD = $(top_srcdir)/src/lib/ebus/libebus.a + +distclean-local: + -rm -f Makefile.in + -rm -rf .libs diff --git a/src/test/command.csv b/src/lib/ebus/test/command.csv similarity index 100% rename from src/test/command.csv rename to src/lib/ebus/test/command.csv diff --git a/src/test/test_commands.cpp b/src/lib/ebus/test/test_commands.cpp similarity index 100% rename from src/test/test_commands.cpp rename to src/lib/ebus/test/test_commands.cpp diff --git a/src/test/test_configfile.cpp b/src/lib/ebus/test/test_configfile.cpp similarity index 100% rename from src/test/test_configfile.cpp rename to src/lib/ebus/test/test_configfile.cpp diff --git a/src/test/test_data.cpp b/src/lib/ebus/test/test_data.cpp similarity index 100% rename from src/test/test_data.cpp rename to src/lib/ebus/test/test_data.cpp diff --git a/src/test/test_decode.cpp b/src/lib/ebus/test/test_decode.cpp similarity index 100% rename from src/test/test_decode.cpp rename to src/lib/ebus/test/test_decode.cpp diff --git a/src/test/test_encode.cpp b/src/lib/ebus/test/test_encode.cpp similarity index 100% rename from src/test/test_encode.cpp rename to src/lib/ebus/test/test_encode.cpp diff --git a/src/test/test_port.cpp b/src/lib/ebus/test/test_port.cpp similarity index 100% rename from src/test/test_port.cpp rename to src/lib/ebus/test/test_port.cpp diff --git a/src/test/test_symbol.cpp b/src/lib/ebus/test/test_symbol.cpp similarity index 97% rename from src/test/test_symbol.cpp rename to src/lib/ebus/test/test_symbol.cpp index 48abdb10..b68ef9df 100644 --- a/src/test/test_symbol.cpp +++ b/src/lib/ebus/test/test_symbol.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) John Baier 2012-2014 + * Copyright (C) John Baier 2014 * * This file is part of ebusd. * diff --git a/src/lib/utils/Makefile.am b/src/lib/utils/Makefile.am new file mode 100644 index 00000000..d10f81d6 --- /dev/null +++ b/src/lib/utils/Makefile.am @@ -0,0 +1,21 @@ +AM_CXXFLAGS = -fpic \ + -Wall \ + -Wextra + +noinst_LIBRARIES = libutils.a + +libutils_a_SOURCES = wqueue.h \ + notify.h \ + appl.cpp \ + appl.h \ + daemon.cpp \ + daemon.h \ + logger.cpp \ + logger.h \ + thread.cpp \ + thread.h \ + tcpsocket.cpp \ + tcpsocket.h + +distclean-local: + -rm -f Makefile.in diff --git a/src/libcore/appl.cpp b/src/lib/utils/appl.cpp similarity index 98% rename from src/libcore/appl.cpp rename to src/lib/utils/appl.cpp index 795898f0..263f9554 100644 --- a/src/libcore/appl.cpp +++ b/src/lib/utils/appl.cpp @@ -62,7 +62,7 @@ void Appl::addItem(const char* name, Param param, const char* shortname, void Appl::printArgs() { std::cerr << std::endl << "Usage:" << std::endl << " " - << m_argv[0].substr(2) << " [OPTIONS...]" ; + << m_argv[0].substr(m_argv[0].find_last_of("/\\") + 1) << " [OPTIONS...]" ; if (m_argTxt.size() != 0) std::cerr << " " << m_argTxt; diff --git a/src/libcore/appl.h b/src/lib/utils/appl.h similarity index 100% rename from src/libcore/appl.h rename to src/lib/utils/appl.h diff --git a/src/libcore/daemon.cpp b/src/lib/utils/daemon.cpp similarity index 100% rename from src/libcore/daemon.cpp rename to src/lib/utils/daemon.cpp diff --git a/src/libcore/daemon.h b/src/lib/utils/daemon.h similarity index 100% rename from src/libcore/daemon.h rename to src/lib/utils/daemon.h diff --git a/src/libcore/logger.cpp b/src/lib/utils/logger.cpp similarity index 100% rename from src/libcore/logger.cpp rename to src/lib/utils/logger.cpp diff --git a/src/libcore/logger.h b/src/lib/utils/logger.h similarity index 100% rename from src/libcore/logger.h rename to src/lib/utils/logger.h diff --git a/src/libcore/notify.h b/src/lib/utils/notify.h similarity index 100% rename from src/libcore/notify.h rename to src/lib/utils/notify.h diff --git a/src/libcore/tcpsocket.cpp b/src/lib/utils/tcpsocket.cpp similarity index 100% rename from src/libcore/tcpsocket.cpp rename to src/lib/utils/tcpsocket.cpp diff --git a/src/libcore/tcpsocket.h b/src/lib/utils/tcpsocket.h similarity index 100% rename from src/libcore/tcpsocket.h rename to src/lib/utils/tcpsocket.h diff --git a/src/libcore/thread.cpp b/src/lib/utils/thread.cpp similarity index 100% rename from src/libcore/thread.cpp rename to src/lib/utils/thread.cpp diff --git a/src/libcore/thread.h b/src/lib/utils/thread.h similarity index 100% rename from src/libcore/thread.h rename to src/lib/utils/thread.h diff --git a/src/libcore/wqueue.h b/src/lib/utils/wqueue.h similarity index 89% rename from src/libcore/wqueue.h rename to src/lib/utils/wqueue.h index 15cca9a0..0509b87e 100644 --- a/src/libcore/wqueue.h +++ b/src/lib/utils/wqueue.h @@ -64,6 +64,20 @@ public: return item; } + T next() + { + pthread_mutex_lock(&m_mutex); + + while (m_queue.size() == 0) + pthread_cond_wait(&m_cond, &m_mutex); + + T item = m_queue.front(); + + pthread_mutex_unlock(&m_mutex); + + return item; + } + int size() { pthread_mutex_lock(&m_mutex); diff --git a/src/libcore/Makefile.am b/src/libcore/Makefile.am deleted file mode 100644 index d1b3b997..00000000 --- a/src/libcore/Makefile.am +++ /dev/null @@ -1,21 +0,0 @@ -AM_CXXFLAGS = -fpic \ - -Wall \ - -Wextra - -noinst_LIBRARIES = libcore.a - -libcore_a_SOURCES = wqueue.h \ - notify.h \ - appl.cpp \ - appl.h \ - daemon.cpp \ - daemon.h \ - logger.cpp \ - logger.h \ - thread.cpp \ - thread.h \ - tcpsocket.cpp \ - tcpsocket.h - -distclean-local: - -rm -f Makefile.in diff --git a/src/libebus/bus.cpp b/src/libebus/bus.cpp deleted file mode 100644 index f0da3073..00000000 --- a/src/libebus/bus.cpp +++ /dev/null @@ -1,388 +0,0 @@ -/* - * Copyright (C) Roland Jax 2012-2014 - * - * This file is part of ebusd. - * - * ebusd 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 3 of the License, or - * (at your option) any later version. - * - * ebusd is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with ebusd. If not, see http://www.gnu.org/licenses/. - */ - -#include "bus.h" -#include -#include - -namespace libebus -{ - - -Bus::Bus(const std::string deviceName, const bool noDeviceCheck, const long recvTimeout, - const std::string dumpFile, const long dumpSize, const bool dumpState) - : m_sstr(), m_recvTimeout(recvTimeout), m_dumpState(dumpState), - m_busLocked(false), m_busPriorRetry(false) -{ - m_port = new Port(deviceName, noDeviceCheck); - m_dump = new Dump(dumpFile, dumpSize); -} - -Bus::~Bus() -{ - if (isConnected() == true) - disconnect(); - - delete m_port; - delete m_dump; -} - -void Bus::printBytes() const -{ - unsigned char byte; - ssize_t bytes_read; - - bytes_read = m_port->recv(0); - - for (int i = 0; i < bytes_read; i++) { - byte = m_port->byte(); - std::cout << std::nouppercase << std::hex << std::setw(2) - << std::setfill('0') << static_cast(byte); - if (byte == SYN) - std::cout << std::endl; - } -} - -int Bus::proceed() -{ - unsigned char byte_recv; - ssize_t bytes_recv; - - // fetch new message and get bus - if (m_sendBuffer.size() != 0 && m_sstr.size() == 0) { - BusCommand* busCommand = m_sendBuffer.front(); - return getBus(busCommand->getCommand()[0]); - } - - // wait for new data - bytes_recv = m_port->recv(0); - - if (bytes_recv < 0) - return RESULT_ERR_DEVICE; - - for (int i = 0; i < bytes_recv; i++) { - - // fetch next byte - byte_recv = recvByte(); - - // store byte - return proceedCycData(byte_recv); // TODO what if more than one byte was received? - } - - return RESULT_SYN; -} - -int Bus::proceedCycData(const unsigned char byte) -{ - if (byte != SYN) { - m_sstr.push_back(byte, true, false); - if (m_busLocked == true) - m_busLocked = false; - - return RESULT_DATA; - } - - if (byte == SYN && m_sstr.size() != 0) { - // lock bus after SYN-BYTE-SYN Sequence - if (m_sstr.size() == 1 && m_busPriorRetry == false) - m_busLocked = true; - - m_cycBuffer.push(m_sstr); - m_sstr.clear(); - - if (m_busLocked == true) - return RESULT_BUS_LOCKED; - } - - return RESULT_SYN; -} - -SymbolString Bus::getCycData() -{ - SymbolString data; - - if (m_cycBuffer.empty() == false) { - data = m_cycBuffer.front(); - m_cycBuffer.pop(); - } - - return data; -} - -int Bus::getBus(const unsigned char byte_sent) -{ - unsigned char byte_recv; - ssize_t bytes_sent, bytes_recv; - - // send QQ - bytes_sent = m_port->send(&byte_sent, 1); - if (bytes_sent <= 0) - return RESULT_ERR_SEND; - - // receive 1 byte - must be QQ - bytes_recv = m_port->recv(0, 1); - - if (bytes_recv < 0) - return RESULT_ERR_DEVICE; - - // fetch next byte - byte_recv = recvByte(); - - // compare sent and received byte - if (bytes_recv == 1 && byte_sent == byte_recv) { - m_busPriorRetry = false; - return RESULT_BUS_ACQUIRED; - } - - // store byte - int ret = proceedCycData(byte_recv); - if (ret >= 0) - return ret; -// TODO this needs to be re-designed with above proceedCycData() - // compare prior nibble for retry - if (bytes_recv == 1 && (byte_sent & 0x0F) == (byte_recv & 0x0F)) { - m_busPriorRetry = true; - return RESULT_BUS_PRIOR_RETRY; - } - - m_busLocked = true; - return RESULT_ERR_BUS_LOST; -} - -BusCommand* Bus::sendCommand() -{ - unsigned char byte_recv; - ssize_t bytes_recv; - std::string result; - SymbolString slaveData; - int retval = RESULT_OK; - - BusCommand* busCommand = m_sendBuffer.front(); - m_sendBuffer.pop(); - - // send ZZ PB SB NN Dx CRC - SymbolString command = busCommand->getCommand(); - for (size_t i = 1; i < command.size(); i++) { - retval = sendByte(command[i]); - if (retval < 0) - goto on_exit; - } - - // BC -> send SYN - if (busCommand->getType() == broadcast) { - sendByte(SYN); - goto on_exit; - } - - // receive ACK - bytes_recv = m_port->recv(m_recvTimeout); - if (bytes_recv > 1) { - retval = RESULT_ERR_EXTRA_DATA; - goto on_exit; - } else if (bytes_recv < 0) { - retval = RESULT_ERR_TIMEOUT; - goto on_exit; - } - - byte_recv = recvByte(); - - // is received byte SYN? - if (byte_recv == SYN) { - retval = RESULT_ERR_SYN; - goto on_exit; - } - - // is slave ACK negative? - if (byte_recv == NAK) { - - // send QQ ZZ PB SB NN Dx CRC again - for (size_t i = 0; i < command.size(); i++) { - retval = sendByte(command[i]); - if (retval < 0) - goto on_exit; - } - - // receive ACK - bytes_recv = m_port->recv(m_recvTimeout); - if (bytes_recv > 1) { - retval = RESULT_ERR_EXTRA_DATA; - goto on_exit; - } else if (bytes_recv < 0) { - retval = RESULT_ERR_TIMEOUT; - goto on_exit; - } - - byte_recv = recvByte(); - - // is received byte SYN? - if (byte_recv == SYN) { - retval = RESULT_ERR_SYN; - goto on_exit; - } - - // is slave ACK negative? - if (byte_recv == NAK) { - retval = sendByte(SYN); - if (retval == 0) - retval = RESULT_ERR_NAK; - - goto on_exit; - } - } - - // MM -> send SYN - if (busCommand->getType() == masterMaster) { - sendByte(SYN); - goto on_exit; - } - - // receive NN, Dx, CRC - retval = recvSlaveDataAndCRC(slaveData); - - // are calculated and received CRC equal? - if (retval == RESULT_ERR_CRC) { - - // send NAK - retval = sendByte(NAK); - if (retval < 0) - goto on_exit; - - // receive NN, Dx, CRC - slaveData.clear(); - retval = recvSlaveDataAndCRC(slaveData); - - // are calculated and received CRC equal? - if (retval == RESULT_ERR_CRC) { - - // send NAK - retval = sendByte(NAK); - if (retval >= 0) - retval = RESULT_ERR_CRC; - } - } - - if (retval < 0) - goto on_exit; - - // send ACK - retval = sendByte(ACK); - if (retval == -1) { - retval = RESULT_ERR_ACK; - goto on_exit; - } - - // MS -> send SYN - sendByte(SYN); - -on_exit: - - // empty receive buffer - while (m_port->size() != 0) - byte_recv = recvByte(); - - busCommand->setResult(slaveData, retval); - return busCommand; - -} - -BusCommand* Bus::delCommand() -{ - BusCommand* busCommand = m_sendBuffer.front(); - m_sendBuffer.pop(); - - busCommand->setResult(SymbolString(), RESULT_ERR_BUS_LOST); - return busCommand; -} - -int Bus::sendByte(const unsigned char byte_sent) -{ - unsigned char byte_recv; - ssize_t bytes_sent, bytes_recv; - - bytes_sent = m_port->send(&byte_sent, 1); - - // receive 1 byte - must be equal - bytes_recv = m_port->recv(RECV_TIMEOUT); - if (bytes_sent != bytes_recv) - return RESULT_ERR_EXTRA_DATA; - - byte_recv = recvByte(); - - if (byte_sent != byte_recv) - return RESULT_ERR_SEND; - - return RESULT_OK; -} - -unsigned char Bus::recvByte() -{ - unsigned char byte_recv; - - // fetch byte - byte_recv = m_port->byte(); - - if (m_dumpState == true) - m_dump->write((const char*) &byte_recv); - - return byte_recv; -} - -int Bus::recvSlaveDataAndCRC(SymbolString& result) -{ - unsigned char byte_recv, crc_calc = 0; - ssize_t bytes_recv; - size_t NN = 0; - bool updateCrc = true; - int retval = 0; - - for (size_t i = 0, needed = 1; i < needed; i++) { - bytes_recv = m_port->recv(RECV_TIMEOUT, 1); - if (bytes_recv < 0) - return RESULT_ERR_TIMEOUT; - - byte_recv = recvByte(); - retval = result.push_back(byte_recv, true, updateCrc); - if (retval < 0) - return retval; - - if (retval == RESULT_IN_ESC) - needed++; - else if (result.size() == 1) { // NN received - NN = result[0]; - needed += NN; - } - else if (NN > 0 && result.size() == 1+NN) {// all data received - updateCrc = false; - crc_calc = result.getCRC(); - needed++; - } - } - - if (retval == RESULT_IN_ESC) - return RESULT_ERR_ESC; - - if (updateCrc || crc_calc != result[result.size()-1]) - return RESULT_ERR_CRC; - - return RESULT_OK; -} - - -} //namespace - diff --git a/src/libebus/bus.h b/src/libebus/bus.h deleted file mode 100644 index d752dbd7..00000000 --- a/src/libebus/bus.h +++ /dev/null @@ -1,89 +0,0 @@ -/* - * Copyright (C) Roland Jax 2012-2014 - * - * This file is part of ebusd. - * - * ebusd 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 3 of the License, or - * (at your option) any later version. - * - * ebusd is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with ebusd. If not, see http://www.gnu.org/licenses/. - */ - -#ifndef LIBEBUS_BUS_H_ -#define LIBEBUS_BUS_H_ - -#include "symbol.h" -#include "result.h" -#include "port.h" -#include "dump.h" -#include "buscommand.h" -#include -#include -#include -#include - -namespace libebus -{ - - -// the maximum time allowed for retrieving a byte from an addressed slave -#define RECV_TIMEOUT 10000 - -class Bus -{ - -public: - Bus(const std::string deviceName, const bool noDeviceCheck, const long recvTimeout, - const std::string dumpFile, const long dumpSize, const bool dumpState); - ~Bus(); - - void connect() { m_port->open(); } - void disconnect() { if (m_port->isOpen() == true) m_port->close(); } - bool isConnected() { return m_port->isOpen(); } - - void printBytes() const; - - int proceed(); - SymbolString getCycData(); - - void addCommand(BusCommand* busCommand) { m_sendBuffer.push(busCommand); } - - int getBus(const unsigned char byte); - BusCommand* sendCommand(); - BusCommand* delCommand(); - - void setDumpState(const bool dumpState) { m_dumpState = dumpState; } - -private: - Port* m_port; - SymbolString m_sstr; - std::queue m_cycBuffer; - std::queue m_sendBuffer; - - const long m_recvTimeout; - - Dump* m_dump; - bool m_dumpState; - - bool m_busLocked; - bool m_busPriorRetry; - - int proceedCycData(const unsigned char byte); - int sendByte(const unsigned char byte_sent); - unsigned char recvByte(); - int recvSlaveDataAndCRC(SymbolString& result); - -}; - - -} //namespace - -#endif // LIBEBUS_BUS_H_ diff --git a/src/libebus/configfile.h b/src/libebus/configfile.h deleted file mode 100644 index 95d778ac..00000000 --- a/src/libebus/configfile.h +++ /dev/null @@ -1,86 +0,0 @@ -/* - * Copyright (C) Roland Jax 2012-2014 - * - * This file is part of ebusd. - * - * ebusd 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 3 of the License, or - * (at your option) any later version. - * - * ebusd is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with ebusd. If not, see http://www.gnu.org/licenses/. - */ - -#ifndef LIBEBUS_CONFIGFILE_H_ -#define LIBEBUS_CONFIGFILE_H_ - -#include "commands.h" -#include -#include - -namespace libebus -{ - -enum FileType { CSV, XML }; - -class ConfigFile -{ - -public: - virtual ~ConfigFile() {} - - virtual void readFile(std::istream& is, Commands& commands) = 0; - -}; - -class ConfigFileCSV : public ConfigFile -{ - -public: - ~ConfigFileCSV() {} - - void readFile(std::istream& is, Commands& commands); - -}; - -class ConfigFileXML : public ConfigFile -{ - -public: - ~ConfigFileXML() {} - - void readFile(std::istream& is, Commands& commands); - -}; - - -class ConfigCommands -{ - -public: - ConfigCommands(const std::string path, const FileType type); - ~ConfigCommands() { delete m_configfile; } - - void setType(const FileType type); - Commands* getCommands(); - -private: - ConfigFile* m_configfile; - std::string m_path; - std::string m_extension; - std::vector m_files; - - void addFiles(const std::string path, const std::string extension); - -}; - - -} //namespace - -#endif // LIBEBUS_CONFIGFILE_H_ diff --git a/src/libebus/port.h b/src/libebus/port.h deleted file mode 100644 index f69ba276..00000000 --- a/src/libebus/port.h +++ /dev/null @@ -1,122 +0,0 @@ -/* - * Copyright (C) Roland Jax 2012-2014 - * - * This file is part of ebusd. - * - * ebusd 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 3 of the License, or - * (at your option) any later version. - * - * ebusd is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with ebusd. If not, see http://www.gnu.org/licenses/. - */ - -#ifndef LIBEBUS_PORT_H_ -#define LIBEBUS_PORT_H_ - -#include -#include -#include -#include - -namespace libebus -{ - -enum DeviceType { SERIAL, NETWORK }; - -#define MAX_READ_SIZE 100 - -class Device -{ - -public: - Device() : m_fd(-1), m_open(false), m_noDeviceCheck(false) {} - virtual ~Device() {} - - virtual void openDevice(const std::string deviceName, const bool noDeviceCheck) = 0; - virtual void closeDevice() = 0; - bool isOpen(); - - ssize_t sendBytes(const unsigned char* buffer, size_t nbytes); - ssize_t recvBytes(const long timeout, size_t maxCount); - - unsigned char getByte(); - ssize_t sizeRecvBuffer() const { return m_recvBuffer.size(); } - -protected: - int m_fd; - bool m_open; - bool m_noDeviceCheck; - std::queue m_recvBuffer; - unsigned char m_buffer[MAX_READ_SIZE]; - -private: - bool isValid(); - -}; - -class DeviceSerial : public Device -{ - -public: - ~DeviceSerial() { closeDevice(); } - - void openDevice(const std::string deviceName, const bool noDeviceCheck); - void closeDevice(); - -private: - termios m_oldSettings; - -}; - -class DeviceNetwork : public Device -{ - -public: - ~DeviceNetwork() { closeDevice(); } - - void openDevice(const std::string deviceName, const bool noDeviceCheck); - void closeDevice(); - -private: - -}; - - -class Port -{ - -public: - Port(const std::string deviceName, const bool noDeviceCheck); - ~Port() { delete m_device; } - - void open() { m_device->openDevice(m_deviceName, m_noDeviceCheck); } - void close() { m_device->closeDevice(); } - bool isOpen() { return m_device->isOpen(); } - - ssize_t send(const unsigned char* buffer, size_t nbytes) - { return m_device->sendBytes(buffer, nbytes); } - ssize_t recv(const long timeout, size_t maxCount=MAX_READ_SIZE) { return m_device->recvBytes(timeout, maxCount); } - - unsigned char byte() { return m_device->getByte(); } - ssize_t size() const { return m_device->sizeRecvBuffer(); } - -private: - std::string m_deviceName; - Device* m_device; - bool m_noDeviceCheck; - - void setType(const DeviceType type); - -}; - - -} //namespace - -#endif // LIBEBUS_PORT_H_ diff --git a/src/test/Makefile.am b/src/test/Makefile.am deleted file mode 100644 index 8d9c0746..00000000 --- a/src/test/Makefile.am +++ /dev/null @@ -1,41 +0,0 @@ -AM_CXXFLAGS = -fpic \ - -Wall \ - -Wextra \ - -I$(top_srcdir)/src/libebus - -noinst_PROGRAMS = test_port \ - test_symbol \ - test_data \ - test_bus \ - test_commands \ - test_configfile \ - test_decode \ - test_encode - -test_port_SOURCES = test_port.cpp -test_port_LDADD = $(top_srcdir)/src/libebus/libebus.a - -test_symbol_SOURCES = test_symbol.cpp -test_symbol_LDADD = $(top_srcdir)/src/libebus/libebus.a - -test_data_SOURCES = test_data.cpp -test_data_LDADD = $(top_srcdir)/src/libebus/libebus.a - -test_bus_SOURCES = test_bus.cpp -test_bus_LDADD = $(top_srcdir)/src/libebus/libebus.a - -test_commands_SOURCES = test_commands.cpp -test_commands_LDADD = $(top_srcdir)/src/libebus/libebus.a - -test_configfile_SOURCES = test_configfile.cpp -test_configfile_LDADD = $(top_srcdir)/src/libebus/libebus.a - -test_decode_SOURCES = test_decode.cpp -test_decode_LDADD = $(top_srcdir)/src/libebus/libebus.a - -test_encode_SOURCES = test_encode.cpp -test_encode_LDADD = $(top_srcdir)/src/libebus/libebus.a - -distclean-local: - -rm -f Makefile.in - -rm -rf .libs diff --git a/src/test/test_bus.cpp b/src/test/test_bus.cpp deleted file mode 100644 index 518ddde3..00000000 --- a/src/test/test_bus.cpp +++ /dev/null @@ -1,58 +0,0 @@ -/* - * Copyright (C) Roland Jax 2012-2014 - * - * This file is part of ebusd. - * - * ebusd 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 3 of the License, or - * (at your option) any later version. - * - * ebusd is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with ebusd. If not, see http://www.gnu.org/licenses/. - */ - -#include "bus.h" -#include -#include - -using namespace libebus; - -int main () -{ - Bus bus("/dev/ttyUSB0", true, 15000, "/tmp/dump_bus.bin", 100, false); - - bus.connect(); - - if (bus.isConnected() == true) - std::cout << "connect successful." << std::endl; - - int cout = 0; - - while (cout++ < 1000) { - if (bus.isConnected() == true) { - bus.printBytes(); - } else { - sleep(5); - bus.connect(); - - if (bus.isConnected() == false) - std::cout << "can't open /dev/ttyUSB0" << std::endl; - else - std::cout << "reconnect successful." << std::endl; - } - } - - bus.disconnect(); - - if (bus.isConnected() == false) - std::cout << "disconnect successful." << std::endl; - - return 0; - -} diff --git a/src/tools/Makefile.am b/src/tools/Makefile.am deleted file mode 100644 index c9b83ddf..00000000 --- a/src/tools/Makefile.am +++ /dev/null @@ -1,17 +0,0 @@ -AM_CXXFLAGS = -fpic \ - -Wall \ - -Wextra \ - -I$(top_srcdir)/src/libcore \ - -I$(top_srcdir)/src/libebus - -bin_PROGRAMS = ebusctl - -ebusctl_SOURCES = ebusctl.cpp - -ebusctl_LDADD = $(top_srcdir)/src/libcore/libcore.a \ - $(top_srcdir)/src/libebus/libebus.a - -distclean-local: - -rm -f Makefile.in - -rm -rf .libs -