From fd11cae7be5bebcae0e4483a532f407e362f1a11 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 14 Jan 2021 19:32:18 +0100 Subject: [PATCH 01/10] printer: helper macros --- serviceinterface/ServiceInterfacePrinter.h | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/serviceinterface/ServiceInterfacePrinter.h b/serviceinterface/ServiceInterfacePrinter.h index fbdccdd1..e898adf6 100644 --- a/serviceinterface/ServiceInterfacePrinter.h +++ b/serviceinterface/ServiceInterfacePrinter.h @@ -2,6 +2,20 @@ #include #endif +//! https://stackoverflow.com/questions/111928/is-there-a-printf-converter-to-print-in-binary-format +//! Can be used to print out binary numbers in human-readable format. +#define BYTE_TO_BINARY_PATTERN "%c%c%c%c%c%c%c%c" +#define BYTE_TO_BINARY(byte) \ + (byte & 0x80 ? '1' : '0'), \ + (byte & 0x40 ? '1' : '0'), \ + (byte & 0x20 ? '1' : '0'), \ + (byte & 0x10 ? '1' : '0'), \ + (byte & 0x08 ? '1' : '0'), \ + (byte & 0x04 ? '1' : '0'), \ + (byte & 0x02 ? '1' : '0'), \ + (byte & 0x01 ? '1' : '0') + + namespace sif { enum PrintLevel { From eb5548333ee365711f78372dd39c6bf48e10aff7 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 14 Jan 2021 20:00:48 +0100 Subject: [PATCH 02/10] added missing include guards --- serviceinterface/ServiceInterfacePrinter.h | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/serviceinterface/ServiceInterfacePrinter.h b/serviceinterface/ServiceInterfacePrinter.h index e898adf6..6b062108 100644 --- a/serviceinterface/ServiceInterfacePrinter.h +++ b/serviceinterface/ServiceInterfacePrinter.h @@ -1,3 +1,6 @@ +#ifndef FSFW_SERVICEINTERFACE_SERVICEINTERFACEPRINTER +#define FSFW_SERVICEINTERFACE_SERVICEINTERFACEPRINTER + #if FSFW_DISABLE_PRINTOUT == 0 #include #endif @@ -52,3 +55,4 @@ void printError(const char* fmt, ...); } +#endif /* FSFW_SERVICEINTERFACE_SERVICEINTERFACEPRINTER */ From f69d6d49c75998d76d30bb51d3b783332283152c Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Fri, 15 Jan 2021 15:21:13 +0100 Subject: [PATCH 03/10] replaced zu with lu --- globalfunctions/arrayprinter.cpp | 3 ++- osal/linux/PosixThread.cpp | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/globalfunctions/arrayprinter.cpp b/globalfunctions/arrayprinter.cpp index 25d6fcf4..b50aeb21 100644 --- a/globalfunctions/arrayprinter.cpp +++ b/globalfunctions/arrayprinter.cpp @@ -10,7 +10,8 @@ void arrayprinter::print(const uint8_t *data, size_t size, OutputType type, } sif::info << "["; #else - sif::printInfo("Printing data with size %zu: [", size); + // TODO: Use %zu or %lu depending on whether C99 support is given. + sif::printInfo("Printing data with size %lu: [", static_cast(size)); #endif if(type == OutputType::HEX) { arrayprinter::printHex(data, size, maxCharPerLine); diff --git a/osal/linux/PosixThread.cpp b/osal/linux/PosixThread.cpp index 2499b442..bd8e7258 100644 --- a/osal/linux/PosixThread.cpp +++ b/osal/linux/PosixThread.cpp @@ -152,7 +152,7 @@ void PosixThread::createTask(void* (*fnc_)(void*), void* arg_) { " the requested " << stackMb << " MB" << std::endl; #else sif::printError("PosixThread::createTask: Insufficient memory for " - "the requested %zu MB\n", stackMb); + "the requested %lu MB\n", static_cast(stackMb)); #endif } else if(errno == EINVAL) { From 05508418a793df4d4c8e1116cf15fe7cbcef5d91 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Fri, 15 Jan 2021 16:32:25 +0100 Subject: [PATCH 04/10] printf support for array printer --- globalfunctions/arrayprinter.cpp | 134 ++++++++++++++++++++----------- globalfunctions/arrayprinter.h | 12 ++- 2 files changed, 95 insertions(+), 51 deletions(-) diff --git a/globalfunctions/arrayprinter.cpp b/globalfunctions/arrayprinter.cpp index b50aeb21..6dc959d7 100644 --- a/globalfunctions/arrayprinter.cpp +++ b/globalfunctions/arrayprinter.cpp @@ -3,64 +3,101 @@ #include void arrayprinter::print(const uint8_t *data, size_t size, OutputType type, - bool printInfo, size_t maxCharPerLine) { + bool printInfo, size_t maxCharPerLine) { #if FSFW_CPP_OSTREAM_ENABLED == 1 - if(printInfo) { - sif::info << "Printing data with size " << size << ": "; - } - sif::info << "["; + if(printInfo) { + sif::info << "Printing data with size " << size << ": "; + } + sif::info << "["; #else - // TODO: Use %zu or %lu depending on whether C99 support is given. - sif::printInfo("Printing data with size %lu: [", static_cast(size)); -#endif - if(type == OutputType::HEX) { - arrayprinter::printHex(data, size, maxCharPerLine); - } - else if (type == OutputType::DEC) { - arrayprinter::printDec(data, size, maxCharPerLine); - } - else if(type == OutputType::BIN) { - arrayprinter::printBin(data, size); - } +#if FSFW_NO_C99_IO == 1 + sif::printInfo("Printing data with size %lu: [", static_cast(size)); +#else + sif::printInfo("Printing data with size %zu: [", size); +#endif /* FSFW_NO_C99_IO == 1 */ +#endif /* FSFW_CPP_OSTREAM_ENABLED == 1 */ + if(type == OutputType::HEX) { + arrayprinter::printHex(data, size, maxCharPerLine); + } + else if (type == OutputType::DEC) { + arrayprinter::printDec(data, size, maxCharPerLine); + } + else if(type == OutputType::BIN) { + arrayprinter::printBin(data, size); + } } void arrayprinter::printHex(const uint8_t *data, size_t size, - size_t maxCharPerLine) { + size_t maxCharPerLine) { #if FSFW_CPP_OSTREAM_ENABLED == 1 - sif::info << std::hex; - for(size_t i = 0; i < size; i++) { - sif::info << "0x" << static_cast(data[i]); - if(i < size - 1){ - sif::info << " , "; - if(i > 0 and i % maxCharPerLine == 0) { - sif::info << std::endl; + sif::info << std::hex; + for(size_t i = 0; i < size; i++) { + sif::info << "0x" << static_cast(data[i]); + if(i < size - 1) { + sif::info << " , "; + if(i > 0 and i % maxCharPerLine == 0) { + sif::info << std::endl; - } - } - } - sif::info << std::dec; - sif::info << "]" << std::endl; + } + } + } + sif::info << std::dec; + sif::info << "]" << std::endl; #else - // how much memory to reserve for printout? + // General format: 0x01, 0x02, 0x03 so it is number of chars times 6 + // plus line break plus small safety margin. + char printBuffer[(size + 1) * 7 + 1]; + size_t currentPos = 0; + for(size_t i = 0; i < size; i++) { + // To avoid buffer overflows. + if(sizeof(printBuffer) - currentPos <= 7) { + break; + } + + currentPos += snprintf(printBuffer + currentPos, 6, "0x%02x", data[i]); + if(i < size - 1) { + currentPos += sprintf(printBuffer + currentPos, ", "); + if(i > 0 and i % maxCharPerLine == 0) { + currentPos += sprintf(printBuffer + currentPos, "\n"); + } + } + } #endif } void arrayprinter::printDec(const uint8_t *data, size_t size, - size_t maxCharPerLine) { + size_t maxCharPerLine) { #if FSFW_CPP_OSTREAM_ENABLED == 1 - sif::info << std::dec; - for(size_t i = 0; i < size; i++) { - sif::info << static_cast(data[i]); - if(i < size - 1){ - sif::info << " , "; - if(i > 0 and i % maxCharPerLine == 0) { - sif::info << std::endl; - } - } - } - sif::info << "]" << std::endl; + sif::info << std::dec; + for(size_t i = 0; i < size; i++) { + sif::info << static_cast(data[i]); + if(i < size - 1){ + sif::info << " , "; + if(i > 0 and i % maxCharPerLine == 0) { + sif::info << std::endl; + } + } + } + sif::info << "]" << std::endl; #else - // how much memory to reserve for printout? + // General format: 32, 243, -12 so it is number of chars times 5 + // plus line break plus small safety margin. + char printBuffer[(size + 1) * 5 + 1]; + size_t currentPos = 0; + for(size_t i = 0; i < size; i++) { + // To avoid buffer overflows. + if(sizeof(printBuffer) - currentPos <= 5) { + break; + } + + currentPos += snprintf(printBuffer + currentPos, 3, "%d", data[i]); + if(i < size - 1) { + currentPos += sprintf(printBuffer + currentPos, ", "); + if(i > 0 and i % maxCharPerLine == 0) { + currentPos += sprintf(printBuffer + currentPos, "\n"); + } + } + } #endif } @@ -68,11 +105,14 @@ void arrayprinter::printBin(const uint8_t *data, size_t size) { #if FSFW_CPP_OSTREAM_ENABLED == 1 sif::info << "\n" << std::flush; for(size_t i = 0; i < size; i++) { - sif::info << "Byte " << i + 1 << ": 0b"<< - std::bitset<8>(data[i]) << ",\n" << std::flush; + sif::info << "Byte " << i + 1 << ": 0b" << std::bitset<8>(data[i]) << "," << std::endl; } sif::info << "]" << std::endl; #else - // how much memory to reserve for printout? + sif::printInfo("\n"); + for(size_t i = 0; i < size; i++) { + sif::printInfo("Byte %d: 0b" BYTE_TO_BINARY_PATTERN ",\n", BYTE_TO_BINARY(data[i])); + } + sif::printInfo("]\n"); #endif } diff --git a/globalfunctions/arrayprinter.h b/globalfunctions/arrayprinter.h index e57d8e04..6dfa6ecd 100644 --- a/globalfunctions/arrayprinter.h +++ b/globalfunctions/arrayprinter.h @@ -1,20 +1,24 @@ #ifndef FRAMEWORK_GLOBALFUNCTIONS_ARRAYPRINTER_H_ #define FRAMEWORK_GLOBALFUNCTIONS_ARRAYPRINTER_H_ + #include #include enum class OutputType { - DEC, - HEX, - BIN + DEC, + HEX, + BIN }; +//! TODO: Write unit tests for this module. namespace arrayprinter { + void print(const uint8_t* data, size_t size, OutputType type = OutputType::HEX, - bool printInfo = true, size_t maxCharPerLine = 12); + bool printInfo = true, size_t maxCharPerLine = 12); void printHex(const uint8_t* data, size_t size, size_t maxCharPerLine = 12); void printDec(const uint8_t* data, size_t size, size_t maxCharPerLine = 12); void printBin(const uint8_t* data, size_t size); + } #endif /* FRAMEWORK_GLOBALFUNCTIONS_ARRAYPRINTER_H_ */ From baba8fa5d796acc11d3a67f1f57ce427147a3fe2 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Fri, 15 Jan 2021 16:34:05 +0100 Subject: [PATCH 05/10] added array printer test stubs --- unittest/tests/globalfunctions/CMakeLists.txt | 3 +++ unittest/tests/globalfunctions/TestArrayPrinter.cpp | 5 +++++ 2 files changed, 8 insertions(+) create mode 100644 unittest/tests/globalfunctions/CMakeLists.txt create mode 100644 unittest/tests/globalfunctions/TestArrayPrinter.cpp diff --git a/unittest/tests/globalfunctions/CMakeLists.txt b/unittest/tests/globalfunctions/CMakeLists.txt new file mode 100644 index 00000000..4ea49bf7 --- /dev/null +++ b/unittest/tests/globalfunctions/CMakeLists.txt @@ -0,0 +1,3 @@ +target_sources(${TARGET_NAME} PRIVATE + TestArrayPrinter.cpp +) diff --git a/unittest/tests/globalfunctions/TestArrayPrinter.cpp b/unittest/tests/globalfunctions/TestArrayPrinter.cpp new file mode 100644 index 00000000..59143619 --- /dev/null +++ b/unittest/tests/globalfunctions/TestArrayPrinter.cpp @@ -0,0 +1,5 @@ +#include + + + + From 73b9d058e5a9fb2b897b0a6e59cb2e51feb7dbb5 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Fri, 15 Jan 2021 16:56:36 +0100 Subject: [PATCH 06/10] updated internal unit test --- unittest/internal/InternalUnitTester.cpp | 15 ++++++++++++++- unittest/internal/InternalUnitTester.h | 2 +- .../internal/globalfunctions/TestArrayPrinter.cpp | 4 ++++ .../internal/globalfunctions/TestArrayPrinter.h | 12 ++++++++++++ .../tests/globalfunctions/TestArrayPrinter.cpp | 5 ----- 5 files changed, 31 insertions(+), 7 deletions(-) create mode 100644 unittest/internal/globalfunctions/TestArrayPrinter.cpp create mode 100644 unittest/internal/globalfunctions/TestArrayPrinter.h delete mode 100644 unittest/tests/globalfunctions/TestArrayPrinter.cpp diff --git a/unittest/internal/InternalUnitTester.cpp b/unittest/internal/InternalUnitTester.cpp index bd41969c..199a3cf0 100644 --- a/unittest/internal/InternalUnitTester.cpp +++ b/unittest/internal/InternalUnitTester.cpp @@ -5,24 +5,37 @@ #include "osal/IntTestSemaphore.h" #include "osal/IntTestMutex.h" #include "serialize/IntTestSerialization.h" +#include "globalfunctions/TestArrayPrinter.h" #include +struct TestConfig { + bool testArrayPrinter; +}; InternalUnitTester::InternalUnitTester() {} InternalUnitTester::~InternalUnitTester() {} -ReturnValue_t InternalUnitTester::performTests() { +ReturnValue_t InternalUnitTester::performTests(struct TestConfig testConfig) { #if FSFW_CPP_OSTREAM_ENABLED == 1 sif::info << "Running internal unit tests.." << std::endl; +#else + sif::printInfo("Running internal unit tests..\n"); #endif + testserialize::test_serialization(); testmq::testMq(); testsemaph::testBinSemaph(); testsemaph::testCountingSemaph(); testmutex::testMutex(); + if(testConfig.testArrayPrinter) { + arrayprinter::testArrayPrinter(); + } + #if FSFW_CPP_OSTREAM_ENABLED == 1 sif::info << "Internal unit tests finished." << std::endl; +#else + sif::printInfo("Running internal unit tests..\n"); #endif return RETURN_OK; } diff --git a/unittest/internal/InternalUnitTester.h b/unittest/internal/InternalUnitTester.h index d0b1c106..e67777b9 100644 --- a/unittest/internal/InternalUnitTester.h +++ b/unittest/internal/InternalUnitTester.h @@ -22,7 +22,7 @@ public: * Some function which calls all other tests * @return */ - virtual ReturnValue_t performTests(); + virtual ReturnValue_t performTests(struct TestConfig testConfig); }; diff --git a/unittest/internal/globalfunctions/TestArrayPrinter.cpp b/unittest/internal/globalfunctions/TestArrayPrinter.cpp new file mode 100644 index 00000000..078134e1 --- /dev/null +++ b/unittest/internal/globalfunctions/TestArrayPrinter.cpp @@ -0,0 +1,4 @@ +#include "TestArrayPrinter.cpp" + +void arrayprinter::testArrayPrinter() { +} diff --git a/unittest/internal/globalfunctions/TestArrayPrinter.h b/unittest/internal/globalfunctions/TestArrayPrinter.h new file mode 100644 index 00000000..b77f1897 --- /dev/null +++ b/unittest/internal/globalfunctions/TestArrayPrinter.h @@ -0,0 +1,12 @@ +#ifndef FSFW_UNITTEST_INTERNAL_GLOBALFUNCTIONS_TESTARRAYPRINTER_H_ +#define FSFW_UNITTEST_INTERNAL_GLOBALFUNCTIONS_TESTARRAYPRINTER_H_ + +namespace arrayprinter { + +void testArrayPrinter(); + +} + + + +#endif /* FSFW_UNITTEST_INTERNAL_GLOBALFUNCTIONS_TESTARRAYPRINTER_H_ */ diff --git a/unittest/tests/globalfunctions/TestArrayPrinter.cpp b/unittest/tests/globalfunctions/TestArrayPrinter.cpp deleted file mode 100644 index 59143619..00000000 --- a/unittest/tests/globalfunctions/TestArrayPrinter.cpp +++ /dev/null @@ -1,5 +0,0 @@ -#include - - - - From 79cf009049675f07e695fe4627b021b5912902e3 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Fri, 15 Jan 2021 17:06:05 +0100 Subject: [PATCH 07/10] updated internal unit tester --- unittest/internal/CMakeLists.txt | 3 ++- unittest/internal/InternalUnitTester.cpp | 5 +---- unittest/internal/InternalUnitTester.h | 7 ++++++- unittest/internal/globalfunctions/CMakeLists.txt | 3 +++ unittest/internal/globalfunctions/TestArrayPrinter.cpp | 2 +- unittest/internal/internal.mk | 1 + 6 files changed, 14 insertions(+), 7 deletions(-) create mode 100644 unittest/internal/globalfunctions/CMakeLists.txt diff --git a/unittest/internal/CMakeLists.txt b/unittest/internal/CMakeLists.txt index 9c24317f..11fd2b2f 100644 --- a/unittest/internal/CMakeLists.txt +++ b/unittest/internal/CMakeLists.txt @@ -4,4 +4,5 @@ target_sources(${TARGET_NAME} PRIVATE ) add_subdirectory(osal) -add_subdirectory(serialize) \ No newline at end of file +add_subdirectory(serialize) +add_subdirectory(globalfunctions) \ No newline at end of file diff --git a/unittest/internal/InternalUnitTester.cpp b/unittest/internal/InternalUnitTester.cpp index 199a3cf0..f89d093a 100644 --- a/unittest/internal/InternalUnitTester.cpp +++ b/unittest/internal/InternalUnitTester.cpp @@ -9,14 +9,11 @@ #include -struct TestConfig { - bool testArrayPrinter; -}; InternalUnitTester::InternalUnitTester() {} InternalUnitTester::~InternalUnitTester() {} -ReturnValue_t InternalUnitTester::performTests(struct TestConfig testConfig) { +ReturnValue_t InternalUnitTester::performTests(struct InternalUnitTester::TestConfig& testConfig) { #if FSFW_CPP_OSTREAM_ENABLED == 1 sif::info << "Running internal unit tests.." << std::endl; #else diff --git a/unittest/internal/InternalUnitTester.h b/unittest/internal/InternalUnitTester.h index e67777b9..ae954c6a 100644 --- a/unittest/internal/InternalUnitTester.h +++ b/unittest/internal/InternalUnitTester.h @@ -4,6 +4,7 @@ #include "UnittDefinitions.h" #include "../../returnvalues/HasReturnvaluesIF.h" + /** * @brief Can be used for internal testing, for example for hardware specific * tests which can not be run on a host-machine. @@ -15,6 +16,10 @@ */ class InternalUnitTester: public HasReturnvaluesIF { public: + struct TestConfig { + bool testArrayPrinter; + }; + InternalUnitTester(); virtual~ InternalUnitTester(); @@ -22,7 +27,7 @@ public: * Some function which calls all other tests * @return */ - virtual ReturnValue_t performTests(struct TestConfig testConfig); + virtual ReturnValue_t performTests(struct InternalUnitTester::TestConfig& testConfig); }; diff --git a/unittest/internal/globalfunctions/CMakeLists.txt b/unittest/internal/globalfunctions/CMakeLists.txt new file mode 100644 index 00000000..4ea49bf7 --- /dev/null +++ b/unittest/internal/globalfunctions/CMakeLists.txt @@ -0,0 +1,3 @@ +target_sources(${TARGET_NAME} PRIVATE + TestArrayPrinter.cpp +) diff --git a/unittest/internal/globalfunctions/TestArrayPrinter.cpp b/unittest/internal/globalfunctions/TestArrayPrinter.cpp index 078134e1..c26faa85 100644 --- a/unittest/internal/globalfunctions/TestArrayPrinter.cpp +++ b/unittest/internal/globalfunctions/TestArrayPrinter.cpp @@ -1,4 +1,4 @@ -#include "TestArrayPrinter.cpp" +#include "TestArrayPrinter.h" void arrayprinter::testArrayPrinter() { } diff --git a/unittest/internal/internal.mk b/unittest/internal/internal.mk index 799fd796..1d4c9c99 100644 --- a/unittest/internal/internal.mk +++ b/unittest/internal/internal.mk @@ -1,3 +1,4 @@ CXXSRC += $(wildcard $(CURRENTPATH)/osal/*.cpp) CXXSRC += $(wildcard $(CURRENTPATH)/serialize/*.cpp) +CXXSRC += $(wildcard $(CURRENTPATH)/globalfunctions/*.cpp) CXXSRC += $(wildcard $(CURRENTPATH)/*.cpp) \ No newline at end of file From eae3175976c55ada568cc6785f10ace3eb27a9ad Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Fri, 15 Jan 2021 17:25:27 +0100 Subject: [PATCH 08/10] repaired internal unit test --- unittest/CMakeLists.txt | 5 ++++- unittest/internal/UnittDefinitions.cpp | 2 +- unittest/internal/osal/IntTestMutex.cpp | 15 ++++++++++----- 3 files changed, 15 insertions(+), 7 deletions(-) diff --git a/unittest/CMakeLists.txt b/unittest/CMakeLists.txt index 119ef243..24f8ef6f 100644 --- a/unittest/CMakeLists.txt +++ b/unittest/CMakeLists.txt @@ -1,2 +1,5 @@ add_subdirectory(internal) -add_subdirectory(tests) \ No newline at end of file + +if(LINK_CATCH2) + add_subdirectory(tests) +endif() \ No newline at end of file diff --git a/unittest/internal/UnittDefinitions.cpp b/unittest/internal/UnittDefinitions.cpp index 517f561a..ed4b59c1 100644 --- a/unittest/internal/UnittDefinitions.cpp +++ b/unittest/internal/UnittDefinitions.cpp @@ -5,7 +5,7 @@ sif::error << "Unit Tester error: Failed at test ID " << errorId << std::endl; #else - sif::printError("Unit Tester error: Failed at test ID 0x%08x", errorId); + sif::printError("Unit Tester error: Failed at test ID %s\n", errorId.c_str()); #endif /* FSFW_CPP_OSTREAM_ENABLED == 1 */ return HasReturnvaluesIF::RETURN_FAILED; } diff --git a/unittest/internal/osal/IntTestMutex.cpp b/unittest/internal/osal/IntTestMutex.cpp index 2a1584b8..13d87a8b 100644 --- a/unittest/internal/osal/IntTestMutex.cpp +++ b/unittest/internal/osal/IntTestMutex.cpp @@ -3,8 +3,8 @@ #include #include -#if defined(hosted) -#include +#if defined(WIN32) || defined(UNIX) +#include #include #include #endif @@ -19,10 +19,11 @@ void testmutex::testMutex() { } // timed_mutex from the C++ library specifies undefined behaviour if // the timed mutex is locked twice from the same thread. -#if defined(hosted) + // TODO: we should pass a define like FSFW_OSAL_HOST to the build. +#if defined(WIN32) || defined(UNIX) // This calls the function from // another thread and stores the returnvalue in a future. - auto future = std::async(&MutexIF::lockMutex, mutex, 1); + auto future = std::async(&MutexIF::lockMutex, mutex, MutexIF::TimeoutType::WAITING, 1); result = future.get(); #else result = mutex->lockMutex(MutexIF::TimeoutType::WAITING, 1); @@ -35,8 +36,12 @@ void testmutex::testMutex() { if(result != HasReturnvaluesIF::RETURN_OK) { unitt::put_error(id); } - result = mutex->unlockMutex(); + + // TODO: we should pass a define like FSFW_OSAL_HOST to the build. +#if !defined(WIN32) && !defined(UNIX) + result = mutex->unlockMutex(); if(result != MutexIF::CURR_THREAD_DOES_NOT_OWN_MUTEX) { unitt::put_error(id); } +#endif } From 38dd2308879d37ca666b308cda743e2c9079c464 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Fri, 15 Jan 2021 17:28:31 +0100 Subject: [PATCH 09/10] fixed syntax error --- unittest/internal/globalfunctions/TestArrayPrinter.h | 2 -- 1 file changed, 2 deletions(-) diff --git a/unittest/internal/globalfunctions/TestArrayPrinter.h b/unittest/internal/globalfunctions/TestArrayPrinter.h index b77f1897..714c3aed 100644 --- a/unittest/internal/globalfunctions/TestArrayPrinter.h +++ b/unittest/internal/globalfunctions/TestArrayPrinter.h @@ -7,6 +7,4 @@ void testArrayPrinter(); } - - #endif /* FSFW_UNITTEST_INTERNAL_GLOBALFUNCTIONS_TESTARRAYPRINTER_H_ */ From a9135696a58b8ec783ffa46770c4869541d21846 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Fri, 15 Jan 2021 18:07:32 +0100 Subject: [PATCH 10/10] array printer tests complete --- globalfunctions/arrayprinter.cpp | 57 +++++++++++-------- globalfunctions/arrayprinter.h | 9 +-- serviceinterface/ServiceInterfaceBuffer.cpp | 4 +- serviceinterface/ServiceInterfaceBuffer.h | 2 + serviceinterface/ServiceInterfaceStream.cpp | 4 ++ serviceinterface/ServiceInterfaceStream.h | 2 + unittest/internal/InternalUnitTester.cpp | 2 +- .../globalfunctions/TestArrayPrinter.cpp | 25 ++++++++ .../globalfunctions/TestArrayPrinter.h | 3 + 9 files changed, 77 insertions(+), 31 deletions(-) diff --git a/globalfunctions/arrayprinter.cpp b/globalfunctions/arrayprinter.cpp index 6dc959d7..7dc056b0 100644 --- a/globalfunctions/arrayprinter.cpp +++ b/globalfunctions/arrayprinter.cpp @@ -2,20 +2,21 @@ #include "../serviceinterface/ServiceInterface.h" #include + void arrayprinter::print(const uint8_t *data, size_t size, OutputType type, bool printInfo, size_t maxCharPerLine) { #if FSFW_CPP_OSTREAM_ENABLED == 1 if(printInfo) { - sif::info << "Printing data with size " << size << ": "; + sif::info << "Printing data with size " << size << ": " << std::endl; } - sif::info << "["; #else #if FSFW_NO_C99_IO == 1 - sif::printInfo("Printing data with size %lu: [", static_cast(size)); + sif::printInfo("Printing data with size %lu: \n", static_cast(size)); #else - sif::printInfo("Printing data with size %zu: [", size); + sif::printInfo("Printing data with size %zu: \n", size); #endif /* FSFW_NO_C99_IO == 1 */ #endif /* FSFW_CPP_OSTREAM_ENABLED == 1 */ + if(type == OutputType::HEX) { arrayprinter::printHex(data, size, maxCharPerLine); } @@ -30,19 +31,23 @@ void arrayprinter::print(const uint8_t *data, size_t size, OutputType type, void arrayprinter::printHex(const uint8_t *data, size_t size, size_t maxCharPerLine) { #if FSFW_CPP_OSTREAM_ENABLED == 1 - sif::info << std::hex; + if(sif::info.crAdditionEnabled()) { + std::cout << "\r" << std::endl; + } + + std::cout << "[" << std::hex; for(size_t i = 0; i < size; i++) { - sif::info << "0x" << static_cast(data[i]); + std::cout << "0x" << static_cast(data[i]); if(i < size - 1) { - sif::info << " , "; - if(i > 0 and i % maxCharPerLine == 0) { - sif::info << std::endl; + std::cout << " , "; + if(i > 0 and (i + 1) % maxCharPerLine == 0) { + std::cout << std::endl; } } } - sif::info << std::dec; - sif::info << "]" << std::endl; + std::cout << std::dec; + std::cout << "]" << std::endl; #else // General format: 0x01, 0x02, 0x03 so it is number of chars times 6 // plus line break plus small safety margin. @@ -57,28 +62,33 @@ void arrayprinter::printHex(const uint8_t *data, size_t size, currentPos += snprintf(printBuffer + currentPos, 6, "0x%02x", data[i]); if(i < size - 1) { currentPos += sprintf(printBuffer + currentPos, ", "); - if(i > 0 and i % maxCharPerLine == 0) { + if(i > 0 and (i + 1) % maxCharPerLine == 0) { currentPos += sprintf(printBuffer + currentPos, "\n"); } } } + printf("[%s]\n", printBuffer); #endif } void arrayprinter::printDec(const uint8_t *data, size_t size, size_t maxCharPerLine) { #if FSFW_CPP_OSTREAM_ENABLED == 1 - sif::info << std::dec; + if(sif::info.crAdditionEnabled()) { + std::cout << "\r" << std::endl; + } + + std::cout << "[" << std::dec; for(size_t i = 0; i < size; i++) { - sif::info << static_cast(data[i]); + std::cout << static_cast(data[i]); if(i < size - 1){ - sif::info << " , "; - if(i > 0 and i % maxCharPerLine == 0) { - sif::info << std::endl; + std::cout << " , "; + if(i > 0 and (i + 1) % maxCharPerLine == 0) { + std::cout << std::endl; } } } - sif::info << "]" << std::endl; + std::cout << "]" << std::endl; #else // General format: 32, 243, -12 so it is number of chars times 5 // plus line break plus small safety margin. @@ -93,26 +103,23 @@ void arrayprinter::printDec(const uint8_t *data, size_t size, currentPos += snprintf(printBuffer + currentPos, 3, "%d", data[i]); if(i < size - 1) { currentPos += sprintf(printBuffer + currentPos, ", "); - if(i > 0 and i % maxCharPerLine == 0) { + if(i > 0 and (i + 1) % maxCharPerLine == 0) { currentPos += sprintf(printBuffer + currentPos, "\n"); } } } + printf("[%s]\n", printBuffer); #endif } void arrayprinter::printBin(const uint8_t *data, size_t size) { #if FSFW_CPP_OSTREAM_ENABLED == 1 - sif::info << "\n" << std::flush; for(size_t i = 0; i < size; i++) { - sif::info << "Byte " << i + 1 << ": 0b" << std::bitset<8>(data[i]) << "," << std::endl; + sif::info << "Byte " << i + 1 << ": 0b" << std::bitset<8>(data[i]) << std::endl; } - sif::info << "]" << std::endl; #else - sif::printInfo("\n"); for(size_t i = 0; i < size; i++) { - sif::printInfo("Byte %d: 0b" BYTE_TO_BINARY_PATTERN ",\n", BYTE_TO_BINARY(data[i])); + sif::printInfo("Byte %d: 0b" BYTE_TO_BINARY_PATTERN "\n", i + 1, BYTE_TO_BINARY(data[i])); } - sif::printInfo("]\n"); #endif } diff --git a/globalfunctions/arrayprinter.h b/globalfunctions/arrayprinter.h index 6dfa6ecd..e6b3ea6b 100644 --- a/globalfunctions/arrayprinter.h +++ b/globalfunctions/arrayprinter.h @@ -10,13 +10,14 @@ enum class OutputType { BIN }; -//! TODO: Write unit tests for this module. namespace arrayprinter { + + void print(const uint8_t* data, size_t size, OutputType type = OutputType::HEX, - bool printInfo = true, size_t maxCharPerLine = 12); -void printHex(const uint8_t* data, size_t size, size_t maxCharPerLine = 12); -void printDec(const uint8_t* data, size_t size, size_t maxCharPerLine = 12); + bool printInfo = true, size_t maxCharPerLine = 10); +void printHex(const uint8_t* data, size_t size, size_t maxCharPerLine = 10); +void printDec(const uint8_t* data, size_t size, size_t maxCharPerLine = 10); void printBin(const uint8_t* data, size_t size); } diff --git a/serviceinterface/ServiceInterfaceBuffer.cpp b/serviceinterface/ServiceInterfaceBuffer.cpp index 1a02d6e9..3f624564 100644 --- a/serviceinterface/ServiceInterfaceBuffer.cpp +++ b/serviceinterface/ServiceInterfaceBuffer.cpp @@ -167,7 +167,9 @@ std::string* ServiceInterfaceBuffer::getPreamble(size_t * preambleSize) { return &preamble; } - +bool ServiceInterfaceBuffer::crAdditionEnabled() const { + return addCrToPreamble; +} #ifdef UT699 #include "../osal/rtems/Interrupt.h" diff --git a/serviceinterface/ServiceInterfaceBuffer.h b/serviceinterface/ServiceInterfaceBuffer.h index b1a50848..9d3ce069 100644 --- a/serviceinterface/ServiceInterfaceBuffer.h +++ b/serviceinterface/ServiceInterfaceBuffer.h @@ -70,6 +70,8 @@ private: void putChars(char const* begin, char const* end); std::string* getPreamble(size_t * preambleSize = nullptr); + + bool crAdditionEnabled() const; }; #endif diff --git a/serviceinterface/ServiceInterfaceStream.cpp b/serviceinterface/ServiceInterfaceStream.cpp index 59526536..ad14cd04 100644 --- a/serviceinterface/ServiceInterfaceStream.cpp +++ b/serviceinterface/ServiceInterfaceStream.cpp @@ -15,5 +15,9 @@ std::string* ServiceInterfaceStream::getPreamble() { return streambuf.getPreamble(); } +bool ServiceInterfaceStream::crAdditionEnabled() const { + return streambuf.crAdditionEnabled(); +} + #endif diff --git a/serviceinterface/ServiceInterfaceStream.h b/serviceinterface/ServiceInterfaceStream.h index f3cb2cd0..e3c0ea7a 100644 --- a/serviceinterface/ServiceInterfaceStream.h +++ b/serviceinterface/ServiceInterfaceStream.h @@ -39,6 +39,8 @@ public: */ std::string* getPreamble(); + bool crAdditionEnabled() const; + protected: ServiceInterfaceBuffer streambuf; }; diff --git a/unittest/internal/InternalUnitTester.cpp b/unittest/internal/InternalUnitTester.cpp index f89d093a..a9394ad3 100644 --- a/unittest/internal/InternalUnitTester.cpp +++ b/unittest/internal/InternalUnitTester.cpp @@ -32,7 +32,7 @@ ReturnValue_t InternalUnitTester::performTests(struct InternalUnitTester::TestCo #if FSFW_CPP_OSTREAM_ENABLED == 1 sif::info << "Internal unit tests finished." << std::endl; #else - sif::printInfo("Running internal unit tests..\n"); + sif::printInfo("Internal unit tests finished.\n"); #endif return RETURN_OK; } diff --git a/unittest/internal/globalfunctions/TestArrayPrinter.cpp b/unittest/internal/globalfunctions/TestArrayPrinter.cpp index c26faa85..de016d19 100644 --- a/unittest/internal/globalfunctions/TestArrayPrinter.cpp +++ b/unittest/internal/globalfunctions/TestArrayPrinter.cpp @@ -1,4 +1,29 @@ #include "TestArrayPrinter.h" void arrayprinter::testArrayPrinter() { + { + const std::array testDataSmall = {0x01, 0x02, 0x03, 0x04, 0x05}; + arrayprinter::print(testDataSmall.data(), testDataSmall.size()); + arrayprinter::print(testDataSmall.data(), testDataSmall.size(), OutputType::DEC); + arrayprinter::print(testDataSmall.data(), testDataSmall.size(), OutputType::BIN); + } + + { + std::array testDataMed; + for(size_t idx = 0; idx < testDataMed.size(); idx ++) { + testDataMed[idx] = testDataMed.size() - idx; + } + arrayprinter::print(testDataMed.data(), testDataMed.size()); + arrayprinter::print(testDataMed.data(), testDataMed.size(), OutputType::DEC, 8); + } + + { + std::array testDataLarge; + for(size_t idx = 0; idx < testDataLarge.size(); idx ++) { + testDataLarge[idx] = idx; + } + arrayprinter::print(testDataLarge.data(), testDataLarge.size()); + arrayprinter::print(testDataLarge.data(), testDataLarge.size(), OutputType::DEC); + } + } diff --git a/unittest/internal/globalfunctions/TestArrayPrinter.h b/unittest/internal/globalfunctions/TestArrayPrinter.h index 714c3aed..50b82ca0 100644 --- a/unittest/internal/globalfunctions/TestArrayPrinter.h +++ b/unittest/internal/globalfunctions/TestArrayPrinter.h @@ -1,6 +1,9 @@ #ifndef FSFW_UNITTEST_INTERNAL_GLOBALFUNCTIONS_TESTARRAYPRINTER_H_ #define FSFW_UNITTEST_INTERNAL_GLOBALFUNCTIONS_TESTARRAYPRINTER_H_ +#include +#include + namespace arrayprinter { void testArrayPrinter();