diff --git a/README.md b/README.md index 03d5df7..488ce96 100644 --- a/README.md +++ b/README.md @@ -14,6 +14,7 @@ - [3.7. Configuring](#37-configuring) - [4. Contributing](#4-contributing) - [4.1. Work Flow](#41-work-flow) + - [4.2. Continuous Integration](#42-continuous-integration) - [5. Version History](#5-version-history) - [5.1. Version 0.5](#51-version-05) - [5.2. Version 0.4](#52-version-04) @@ -110,8 +111,13 @@ I Use [Git flow](https://danielkummer.github.io/git-flow-cheatsheet/) as my work - You have tested your code thoroughly - Compilation produces no warnings - Code formating rules are observed (these are very lousy though) +## 4.2. Continuous Integration +I have added some basic CI using CircleCI [![F4FXL](https://circleci.com/gh/F4FXL/DStarGateway.svg?style=svg)](https://app.circleci.com/pipelines/github/F4FXL/DStarGateway?filter=all) I am trying to rewrite the code so that it can be put into some Behavior Driven Development scheme. This is a long haul task and I'll try do do it on the go while changing/adding stuff. +the testing framwrok used is Google Test. + # 5. Version History ## 5.1. Version 0.5 +- [Bugfix] Remote control connection failed ([#13](https://github.com/F4FXL/DStarGateway/issues/13)) - [Bugfix] Trying to connect to ghost ircDDB when no ircDDB is configured ## 5.2. Version 0.4 - [Improvement] Add APRS status link feature ([#8](https://github.com/F4FXL/DStarGateway/issues/8)) diff --git a/RemoteHandler.cpp b/RemoteHandler.cpp index d4f4df2..7372e98 100644 --- a/RemoteHandler.cpp +++ b/RemoteHandler.cpp @@ -62,6 +62,7 @@ void CRemoteHandler::process() m_handler.sendRandom(m_random); break; case RPHT_HASH: { + CLog::logTrace("Read Hash %X", m_random); bool valid = m_handler.readHash(m_password, m_random); if (valid) { CLog::logInfo("Remote control user has logged in"); diff --git a/RemoteProtocolHandler.cpp b/RemoteProtocolHandler.cpp index e4857b2..0c6a026 100644 --- a/RemoteProtocolHandler.cpp +++ b/RemoteProtocolHandler.cpp @@ -25,6 +25,7 @@ #include "SHA256.h" #include "Utils.h" #include "StringUtils.h" +#include "Log.h" const unsigned int BUFFER_LENGTH = 2000U; @@ -226,7 +227,7 @@ bool CRemoteProtocolHandler::readLink(std::string& callsign, RECONNECT& reconnec int32_t temp; ::memcpy(&temp, m_inBuffer + 3U + LONG_CALLSIGN_LENGTH, sizeof(int32_t)); - reconnect = RECONNECT(CUtils::swap_endian(temp)); + reconnect = RECONNECT(CUtils::swap_endian_be(temp)); reflector = std::string((char*)(m_inBuffer + 3U + LONG_CALLSIGN_LENGTH + sizeof(int32_t)),LONG_CALLSIGN_LENGTH); @@ -245,7 +246,7 @@ bool CRemoteProtocolHandler::readUnlink(std::string& callsign, PROTOCOL& protoco int32_t temp; ::memcpy(&temp, m_inBuffer + 3U + LONG_CALLSIGN_LENGTH, sizeof(int32_t)); - protocol = PROTOCOL(CUtils::swap_endian(temp)); + protocol = PROTOCOL(CUtils::swap_endian_be(temp)); reflector = std::string((char*)(m_inBuffer + 3U + LONG_CALLSIGN_LENGTH + sizeof(int32_t)),LONG_CALLSIGN_LENGTH); @@ -315,7 +316,7 @@ bool CRemoteProtocolHandler::sendRepeater(const CRemoteRepeaterData& data) p[i] = data.getCallsign()[i]; p += LONG_CALLSIGN_LENGTH; - int32_t reconnect = CUtils::swap_endian(data.getReconnect()); + int32_t reconnect = CUtils::swap_endian_be(data.getReconnect()); ::memcpy(p, &reconnect, sizeof(int32_t)); p += sizeof(int32_t); @@ -332,19 +333,19 @@ bool CRemoteProtocolHandler::sendRepeater(const CRemoteRepeaterData& data) p[i] = link->getCallsign()[i]; p += LONG_CALLSIGN_LENGTH; - int32_t protocol = CUtils::swap_endian(link->getProtocol()); + int32_t protocol = CUtils::swap_endian_be(link->getProtocol()); ::memcpy(p, &protocol, sizeof(int32_t)); p += sizeof(int32_t); - int32_t linked = CUtils::swap_endian(link->isLinked()); + int32_t linked = CUtils::swap_endian_be(link->isLinked()); ::memcpy(p, &linked, sizeof(int32_t)); p += sizeof(int32_t); - int32_t direction = CUtils::swap_endian(link->getDirection()); + int32_t direction = CUtils::swap_endian_be(link->getDirection()); ::memcpy(p, &direction, sizeof(int32_t)); p += sizeof(int32_t); - int32_t dongle = CUtils::swap_endian(link->isDongle()); + int32_t dongle = CUtils::swap_endian_be(link->isDongle()); ::memcpy(p, &dongle, sizeof(int32_t)); p += sizeof(int32_t); } @@ -440,7 +441,8 @@ bool CRemoteProtocolHandler::sendRandom(uint32_t random) { ::memcpy(m_outBuffer + 0U, "RND", 3U); - uint32_t temp = CUtils::swap_endian(random); + CLog::logTrace("Send Random %X", random); + uint32_t temp = CUtils::swap_endian_be(random); ::memcpy(m_outBuffer + 3U, &temp, sizeof(uint32_t)); // CUtils::dump("Outgoing", m_outBuffer, 3U + sizeof(uint32_t)); diff --git a/Tests/Utils/swap_endian.cpp b/Tests/Utils/swap_endian.cpp new file mode 100644 index 0000000..767d10e --- /dev/null +++ b/Tests/Utils/swap_endian.cpp @@ -0,0 +1,33 @@ +/* + * Copyright (c) 2021 by Geoffrey Merck F4FXL / KC3FRA + * + * This program 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 2 of the License, or + * (at your option) any later version. + * + * This program 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 this program; if not, write to the Free Software + * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + */ + +#include + +#include "../../Utils.h" + +class Utils_swap_endian : public ::testing::Test { + +}; + +TEST_F(Utils_swap_endian, SwapUINT32) { + uint32_t test = 0x12345678U; + + uint32_t res = CUtils::swap_endian(test); + + EXPECT_EQ(res, 0x78563412U); +} \ No newline at end of file diff --git a/Tests/Utils/swap_endian_be.cpp b/Tests/Utils/swap_endian_be.cpp new file mode 100644 index 0000000..7099a0e --- /dev/null +++ b/Tests/Utils/swap_endian_be.cpp @@ -0,0 +1,34 @@ +/* + * Copyright (c) 2021 by Geoffrey Merck F4FXL / KC3FRA + * + * This program 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 2 of the License, or + * (at your option) any later version. + * + * This program 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 this program; if not, write to the Free Software + * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + */ + +#include + +#include "../../Utils.h" + +class Utils_swap_endian_be : public ::testing::Test { + +}; + +// This test will fail on big endian systems.... +TEST_F(Utils_swap_endian_be, SwapUINT32_be) { + uint32_t test = 0x12345678U; + + uint32_t res = CUtils::swap_endian_be(test); + + EXPECT_EQ(res, 0x12345678U); +} \ No newline at end of file diff --git a/Utils.h b/Utils.h index 61fa0fb..0e60527 100644 --- a/Utils.h +++ b/Utils.h @@ -66,4 +66,25 @@ public: return dest.u; } + + // https://stackoverflow.com/questions/1001307/detecting-endianness-programmatically-in-a-c-program + static bool is_big_endian() + { + union { + uint32_t i; + char c[4]; + } bint = {0x01020304}; + + return bint.c[0] == 1; + } + + // Ersatz for macro wxINT32_SWAP_ON_BE + template + static T swap_endian_be(T u) + { + if(is_big_endian()) + return swap_endian(u); + + return u; + } };