diff --git a/.idea/codeStyles/Project.xml b/.idea/codeStyles/Project.xml index 86ab48c81e5496caa2fb05e7674831c28008b715..f25060c0a0ccdd77d361f71cffaeeb85e993991b 100644 --- a/.idea/codeStyles/Project.xml +++ b/.idea/codeStyles/Project.xml @@ -3,25 +3,6 @@ <option name="RIGHT_MARGIN" value="100" /> <option name="WRAP_WHEN_TYPING_REACHES_RIGHT_MARGIN" value="true" /> <Objective-C-extensions> - <file> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Import" /> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Macro" /> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Typedef" /> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Enum" /> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Constant" /> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Global" /> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Struct" /> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="FunctionPredecl" /> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Function" /> - </file> - <class> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Property" /> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Synthesize" /> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="InitMethod" /> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="StaticMethod" /> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="InstanceMethod" /> - <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="DeallocMethod" /> - </class> <extensions> <pair source="cpp" header="hpp" fileNamingConvention="PASCAL_CASE" /> <pair source="c" header="h" fileNamingConvention="NONE" /> diff --git a/CMakeLists.txt b/CMakeLists.txt index d9e456e694733af386d637fdc9dda03397959904..069449e4ee81f587493231d3ddd25c85991fa562 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -17,7 +17,7 @@ add_custom_target(check add_library(common OBJECT src/ErrorHandler.cpp src/Message.cpp - src/MessageParser.cpp + src/MessageParser.cpp src/Helpers/CRCHelper.cpp src/Helpers/TimeHelper.cpp src/Services/EventReportService.cpp @@ -26,6 +26,7 @@ add_library(common OBJECT src/Services/RequestVerificationService.cpp src/Services/TestService.cpp src/Services/TimeManagementService.cpp + src/Services/EventActionService.cpp ) # Specify the .cpp files for the executables @@ -44,6 +45,7 @@ IF (EXISTS "${PROJECT_SOURCE_DIR}/lib/Catch2/CMakeLists.txt") add_executable(tests $<TARGET_OBJECTS:common> ${test_main_SRC} - ${test_SRC}) + ${test_SRC} + ) target_link_libraries(tests Catch2::Catch2) ENDIF () diff --git a/inc/ErrorHandler.hpp b/inc/ErrorHandler.hpp index adffdc132bffd5aa7830bcbd414f415a643c6340..95c9138e1824f52e1acf152aaa0c7c4b2d8d7e73 100644 --- a/inc/ErrorHandler.hpp +++ b/inc/ErrorHandler.hpp @@ -51,7 +51,6 @@ public: * A string is larger than the largest allowed string */ StringTooLarge = 4, - /** * An error in the header of a packet makes it unable to be parsed */ diff --git a/inc/Message.hpp b/inc/Message.hpp index 0d4aa67d8e47cd6ee6045a48015991f93d78bf3d..ecee3cb27ba37675e4a8398294f338fc4d2c6352 100644 --- a/inc/Message.hpp +++ b/inc/Message.hpp @@ -20,6 +20,8 @@ class Message; */ class Message { public: + Message () = default; + enum PacketType { TM = 0, // Telemetry TC = 1 // Telecommand diff --git a/inc/MessageParser.hpp b/inc/MessageParser.hpp index 0af0afbf7bf55f278c9bc69f27688dc56b4560b6..0ffa87e3aa792dd43ba474f93ab43e3747b1c5f5 100644 --- a/inc/MessageParser.hpp +++ b/inc/MessageParser.hpp @@ -1,16 +1,20 @@ #ifndef ECSS_SERVICES_MESSAGEPARSER_HPP #define ECSS_SERVICES_MESSAGEPARSER_HPP +#include <Services/EventActionService.hpp> #include "Message.hpp" /** * A generic class responsible for the execution of the incoming telemetry and telecommand * packets. * + * @todo Make the connection between the ST[01]-request verification service and the services + * that initiate it * @todo Implement the execute function in the upcoming services or generally in the upcoming * activities * */ + class MessageParser { public: @@ -32,7 +36,17 @@ public: * @param length The size of the message * @return A new object that represents the parsed message */ - Message parse(uint8_t * data, uint32_t length); + Message parse(uint8_t *data, uint32_t length); + + /** + * @todo: elaborate on this comment + * Create a message so that a string can be parsed + * + * Note: conversion of char* to unsigned char* should flow without any problems according to + * this great analysis: + * stackoverflow.com/questions/15078638/can-i-turn-unsigned-char-into-char-and-vice-versa + */ + Message parseRequestTC(String<ECSS_EVENT_SERVICE_STRING_SIZE> data); private: /** diff --git a/inc/Services/EventActionService.hpp b/inc/Services/EventActionService.hpp new file mode 100644 index 0000000000000000000000000000000000000000..338a67345c0163bb8df8708f784c0b7aae868edc --- /dev/null +++ b/inc/Services/EventActionService.hpp @@ -0,0 +1,126 @@ +#ifndef ECSS_SERVICES_EVENTACTIONSERVICE_HPP +#define ECSS_SERVICES_EVENTACTIONSERVICE_HPP + +#define ECSS_EVENT_SERVICE_STRING_SIZE 64 + +#define ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE 256 + +#include "Service.hpp" +#include "MessageParser.hpp" +#include "etl/String.hpp" +#include <Services/EventReportService.hpp> + +/** + * Implementation of ST[19] event-action Service + * + * ECSS 8.19 && 6.19 + * + * @todo: Use an etl::list instead of eventActionDefinitionArray + * @todo: (Possible) Use a etl::map for eventActionDefinitionArray + * @todo: check if executeAction should accept applicationID too + * @todo: Since there are multiple actions per event and in delete/enable/disable functions are + * multiple instances are accessed, should I find a more efficient way to access them? + * @todo: check if eventActionFunctionStatus should be private or not + * @todo: check if eventAction array of definitions should be private or not + * @todo: check size of eventActionDefinitionArray + */ +class EventActionService : public Service { +private: + + /** + * Event-action function status + */ + bool eventActionFunctionStatus; + + /** + * Custom function that is called right after an event takes place, to initiate + * the execution of the action + */ + void executeAction(uint16_t eventID); + +public: + struct EventActionDefinition { + bool empty = true; + // TODO: APID = 0 is the Ground Station APID. This should be changed + uint16_t applicationId = 0; + uint16_t eventDefinitionID = 65535; + String<64> request = ""; + bool enabled = false; + }; + + friend EventReportService; + + EventActionDefinition eventActionDefinitionArray[ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE]; + + EventActionService() { + serviceType = 19; + eventActionFunctionStatus = true; + } + + /** + * TC[19,1] add event-action definitions + * + * Note: We have abolished multiple additions in one Telecommand packet. Only one + * event-action definition will be added per TC packet. That means there will be just an + * application ID, an event definition ID and the TC request. + */ + void addEventActionDefinitions(Message message); + + /** + * TC[19,2] delete event-action definitions + */ + void deleteEventActionDefinitions(Message message); + + /** + * TC[19,3] delete all event-action definitions + */ + void deleteAllEventActionDefinitions(Message message); + + /** + * TC[19,4] enable event-action definitions + */ + void enableEventActionDefinitions(Message message); + + /** + * TC[19,5] disable event-action definitions + */ + void disableEventActionDefinitions(Message message); + + /** + * TC[19,6] report the status of each event-action definition + */ + void requestEventActionDefinitionStatus(Message message); + + /** + * TM[19,7] event-action status report + */ + void eventActionStatusReport(); + + /** + * TC[19,8] enable the event-action function + */ + void enableEventActionFunction(Message message); + + /** + * TC[19,9] disable the event-actioni function + */ + void disableEventActionFunction(Message message); + + /** + * Setter for event-action function status + */ + void setEventActionFunctionStatus(bool status) { + eventActionFunctionStatus = status; + } + + /** + * Getter for event-action function status + * @return eventActionFunctionStatus + */ + bool getEventActionFunctionStatus(){ + return eventActionFunctionStatus; + } + +}; + +#endif //ECSS_SERVICES_EVENTACTIONSERVICE_HPP diff --git a/inc/Services/EventReportService.hpp b/inc/Services/EventReportService.hpp index 5d17779bf78e0bfa7a59437688e3de938db81ed3..92c75eb2962c0dfba40d1723ab1ae893964e4031 100644 --- a/inc/Services/EventReportService.hpp +++ b/inc/Services/EventReportService.hpp @@ -5,10 +5,9 @@ #include <bitset> /** * Implementation of ST[05] event reporting service - * @todo add enum event definition id (and maybe some appending?) - * - * @todo add more enums event IDs * + * @todo: add more enums event IDs + * @todo: Make sure there isn't an event ID == 0, because there's a confliction with another service * Note: enum IDs are these just for test purposes * */ diff --git a/src/MessageParser.cpp b/src/MessageParser.cpp index fe2426e5d394ca2d63e6036793417267e645ad47..33b5574da44deec320cae4a7e6364e194825f885 100644 --- a/src/MessageParser.cpp +++ b/src/MessageParser.cpp @@ -1,4 +1,5 @@ #include <cstring> +#include <Services/EventActionService.hpp> #include "ErrorHandler.hpp" #include "MessageParser.hpp" #include "macros.hpp" @@ -74,3 +75,11 @@ void MessageParser::parseTC(uint8_t *data, uint16_t length, Message &message) { memcpy(message.data, data + 5, length); message.dataSize = length; } + +Message MessageParser::parseRequestTC(String<ECSS_EVENT_SERVICE_STRING_SIZE> data) { + Message message; + uint8_t *dataInt = reinterpret_cast<uint8_t *>(data.data()); + message.packetType = Message::TC; + parseTC(dataInt, ECSS_EVENT_SERVICE_STRING_SIZE, message); + return message; +} diff --git a/src/Services/EventActionService.cpp b/src/Services/EventActionService.cpp new file mode 100644 index 0000000000000000000000000000000000000000..38e3b64ab22bbac6aca19d0fb3c3fab09cfdeb45 --- /dev/null +++ b/src/Services/EventActionService.cpp @@ -0,0 +1,206 @@ +#include "Services/EventActionService.hpp" +#include "Message.hpp" +#include "MessageParser.hpp" + +/** + * @todo: Check if a uint16_t is needed (in case of changing the size of + * eventActionDefinitionArray + */ +void EventActionService::addEventActionDefinitions(Message message) { + // TC[19,1] + + if (message.messageType == 1 && message.packetType == Message::TC && message.serviceType == + 19) { + uint16_t index; + uint16_t applicationID = message.readEnum16(); + uint16_t eventDefinitionID = message.readEnum16(); + bool accepted = true; + for (index = 0; index < ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE; index++) { + if (eventActionDefinitionArray[index].applicationId == applicationID && + eventActionDefinitionArray[index].eventDefinitionID == eventDefinitionID && + eventActionDefinitionArray[index].enabled == true) { + // @todo: throw a failed start of execution error + accepted = false; + } + } + if (accepted){ + for (index = 0; index < ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE; index++) { + // @todo: throw an error if it's full + if (eventActionDefinitionArray[index].empty == true) { + break; + } + } + if (index < ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE) { + eventActionDefinitionArray[index].empty = false; + eventActionDefinitionArray[index].enabled = true; + eventActionDefinitionArray[index].applicationId = applicationID; + eventActionDefinitionArray[index].eventDefinitionID = eventDefinitionID; + if (message.dataSize - 4 > ECSS_EVENT_SERVICE_STRING_SIZE) { + ErrorHandler::reportInternalError(ErrorHandler::InternalErrorType::MessageTooLarge); + } else { + char data[ECSS_EVENT_SERVICE_STRING_SIZE]; + message.readString(data, message.dataSize - 4); + eventActionDefinitionArray[index].request = String<ECSS_EVENT_SERVICE_STRING_SIZE>( + data); + } + } + } + } +} + +void EventActionService::deleteEventActionDefinitions(Message message) { + // TC[19,2] + if (message.messageType == 2 && message.packetType == Message::TC && message.serviceType + == 19) { + uint16_t numberOfEventActionDefinitions = message.readUint16(); + for (uint16_t i = 0; i < numberOfEventActionDefinitions; i++) { + uint16_t applicationID = message.readEnum16(); + uint16_t eventDefinitionID = message.readEnum16(); + for (uint16_t index = 0; index < ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE; index++) { + if (eventActionDefinitionArray[index].applicationId == applicationID && + eventActionDefinitionArray[index].eventDefinitionID == eventDefinitionID && + eventActionDefinitionArray[index].enabled == true) { + eventActionDefinitionArray[index].empty = true; + eventActionDefinitionArray[index].eventDefinitionID = 65535; + eventActionDefinitionArray[index].request = ""; + eventActionDefinitionArray[index].applicationId = 0; + eventActionDefinitionArray[index].enabled = false; + } + } + } + + } +} + +void EventActionService::deleteAllEventActionDefinitions(Message message) { + // TC[19,3] + if (message.messageType == 3 && message.packetType == Message::TC && message.serviceType + == 19) { + setEventActionFunctionStatus(false); + for (uint16_t index = 0; index < ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE; index++) { + if (eventActionDefinitionArray[index].empty == false) { + eventActionDefinitionArray[index].empty = true; + eventActionDefinitionArray[index].enabled = false; + eventActionDefinitionArray[index].eventDefinitionID = 65535; + eventActionDefinitionArray[index].request = ""; + eventActionDefinitionArray[index].applicationId = 0; + } + } + } +} + +void EventActionService::enableEventActionDefinitions(Message message) { + // TC[19,4] + if (message.messageType == 4 && message.packetType == Message::TC && message.serviceType + == 19) { + uint16_t numberOfEventActionDefinitions = message.readUint16(); + if (numberOfEventActionDefinitions != 0){ + for (uint16_t i = 0; i < numberOfEventActionDefinitions; i++) { + uint16_t applicationID = message.readEnum16(); + uint16_t eventDefinitionID = message.readEnum16(); + for (uint16_t index = 0; index < ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE; index++) { + if (eventActionDefinitionArray[index].applicationId == applicationID && + eventActionDefinitionArray[index].eventDefinitionID == eventDefinitionID) { + eventActionDefinitionArray[index].enabled = true; + } + } + } + } else { + for (uint16_t index = 0; index < ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE; index++) { + if (eventActionDefinitionArray[index].empty == false){ + eventActionDefinitionArray[index].enabled = true; + } + } + } + } +} + +void EventActionService::disableEventActionDefinitions(Message message) { + // TC[19,5] + if (message.messageType == 5 && message.packetType == Message::TC && message.serviceType + == 19) { + uint16_t numberOfEventActionDefinitions = message.readUint16(); + if (numberOfEventActionDefinitions != 0){ + for (uint16_t i = 0; i < numberOfEventActionDefinitions; i++) { + uint16_t applicationID = message.readEnum16(); + uint16_t eventDefinitionID = message.readEnum16(); + for (uint16_t index = 0; index < ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE; index++) { + if (eventActionDefinitionArray[index].applicationId == applicationID && + eventActionDefinitionArray[index].eventDefinitionID == eventDefinitionID) { + eventActionDefinitionArray[index].enabled = false; + } + } + } + } else { + for (uint16_t index = 0; index < ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE; index++) { + if (eventActionDefinitionArray[index].empty == false){ + eventActionDefinitionArray[index].enabled = false; + } + } + } + } +} + +void EventActionService::requestEventActionDefinitionStatus(Message message) { + // TC[19,6] + if (message.messageType == 6 && message.packetType == Message::TC && message.serviceType + == 19) { + eventActionStatusReport(); + } +} + +void EventActionService::eventActionStatusReport() { + // TM[19,7] + Message report = createTM(7); + uint8_t count = 0; + for (uint16_t i = 0; i < ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE; i++) { + if (eventActionDefinitionArray[i].empty == false) { + count++; + } + } + report.appendUint8(count); + for (uint16_t i = 0; i < ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE; i++) { + if (eventActionDefinitionArray[i].empty == false) { + report.appendEnum16(eventActionDefinitionArray[i].applicationId); + report.appendEnum16(eventActionDefinitionArray[i].eventDefinitionID); + report.appendBoolean(eventActionDefinitionArray[i].enabled); + } + } + storeMessage(report); +} + +void EventActionService::enableEventActionFunction(Message message) { + // TC[19,8] + if (message.messageType == 8 && message.packetType == Message::TC && message.serviceType + == 19) { + setEventActionFunctionStatus(true); + } +} + +void EventActionService::disableEventActionFunction(Message message) { + // TC[19,9] + if (message.messageType == 9 && message.packetType == Message::TC && message.serviceType + == 19) { + setEventActionFunctionStatus(false); + } +} + +// Should I use the name execute here instead of executeAction? +// Should I use applicationID too? +void EventActionService::executeAction(uint16_t eventID) { + // Custom function + if (eventActionFunctionStatus) { + for (uint16_t i = 0; i < ECSS_EVENT_ACTION_STRUCT_ARRAY_SIZE; i++) { + if (eventActionDefinitionArray[i].empty == false && + eventActionDefinitionArray[i].enabled == + true) { + if (eventActionDefinitionArray[i].eventDefinitionID == eventID) { + MessageParser messageParser; + Message message = messageParser.parseRequestTC( + eventActionDefinitionArray[i].request); + messageParser.execute(message); + } + } + } + } +} diff --git a/src/Services/EventReportService.cpp b/src/Services/EventReportService.cpp index f0326119bfd473332673265aa1e6635d7f0477d3..2c243c25517806fd45b5acd1f012081d85c298ca 100644 --- a/src/Services/EventReportService.cpp +++ b/src/Services/EventReportService.cpp @@ -1,5 +1,5 @@ #include <Services/EventReportService.hpp> -#include "Services/EventReportService.hpp" +#include <Services/EventActionService.hpp> #include "Message.hpp" /** @@ -12,6 +12,8 @@ void EventReportService::informativeEventReport(Event eventID, String<64> data) Message report = createTM(1); report.appendEnum16(eventID); report.appendString(data); + EventActionService eventActionService; + eventActionService.executeAction(eventID); storeMessage(report); } @@ -29,6 +31,8 @@ EventReportService::lowSeverityAnomalyReport(Event eventID, String<64> data) { lastLowSeverityReportID = static_cast<uint16_t >(eventID); storeMessage(report); + EventActionService eventActionService; + eventActionService.executeAction(eventID); } } @@ -43,6 +47,8 @@ void EventReportService::mediumSeverityAnomalyReport(Event eventID, String<64> d lastMediumSeverityReportID = static_cast<uint16_t >(eventID); storeMessage(report); + EventActionService eventActionService; + eventActionService.executeAction(eventID); } } @@ -58,6 +64,8 @@ EventReportService::highSeverityAnomalyReport(Event eventID, String<64> data) { lastHighSeverityReportID = static_cast<uint16_t >(eventID); storeMessage(report); + EventActionService eventActionService; + eventActionService.executeAction(eventID); } } diff --git a/src/main.cpp b/src/main.cpp index bcc262edea6839be3fdee14bebf64daf2f0a1859..bc6fcc911e3b2f95cb29861c14fde59f7affcb05 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -7,6 +7,7 @@ #include "Services/MemoryManagementService.hpp" #include "Services/EventReportService.hpp" #include "Services/TimeManagementService.hpp" +#include "Services/EventActionService.hpp" #include "Message.hpp" #include "MessageParser.hpp" #include "Services/MemoryManagementService.hpp" @@ -183,7 +184,7 @@ int main() { // ST[05] (5,5 to 5,8) test [works] EventReportService::Event eventIDs[] = {EventReportService::HighSeverityUnknownEvent, - EventReportService::MediumSeverityUnknownEvent}; + EventReportService::MediumSeverityUnknownEvent}; EventReportService::Event eventIDs2[] = {EventReportService::HighSeverityUnknownEvent}; Message eventMessage(5, 6, Message::TC, 1); eventMessage.appendUint16(2); @@ -200,5 +201,67 @@ int main() { eventReportService.enableReportGeneration(eventMessage2); eventReportService.requestListOfDisabledEvents(eventMessage3); + // ST[19] test + + EventActionService eventActionService; + Message eventActionDefinition(19, 1, Message::TC, 1); + eventActionDefinition.appendEnum16(0); + eventActionDefinition.appendEnum16(2); + String<64> TCdata = "hi"; + eventActionDefinition.appendString(TCdata); + eventActionService.addEventActionDefinitions(eventActionDefinition); + Message eventActionDefinition1(19, 1, Message::TC, 1); + eventActionDefinition1.appendEnum16(0); + eventActionDefinition1.appendEnum16(2); + TCdata = "hi1"; + eventActionDefinition1.appendString(TCdata); + eventActionService.addEventActionDefinitions(eventActionDefinition1); + Message eventActionDefinition2(19, 1, Message::TC, 1); + eventActionDefinition2.appendEnum16(0); + eventActionDefinition2.appendEnum16(3); + TCdata = "hi2"; + eventActionDefinition2.appendString(TCdata); + eventActionService.addEventActionDefinitions(eventActionDefinition2); + Message eventActionDefinition3(19, 5, Message::TC, 1); + eventActionDefinition3.appendUint16(2); + eventActionDefinition3.appendUint16(0); + eventActionDefinition3.appendUint16(2); + eventActionDefinition3.appendUint16(0); + eventActionDefinition3.appendUint16(3); + + eventActionService.disableEventActionDefinitions(eventActionDefinition3); + std::cout << "Status of position 0,1,2 should be 000:" << eventActionService + .eventActionDefinitionArray[0].enabled << eventActionService + .eventActionDefinitionArray[1].enabled << + eventActionService.eventActionDefinitionArray[2].enabled; + + Message eventActionDefinition5(19, 4, Message::TC, 1); + eventActionDefinition5.appendUint16(2); + eventActionDefinition5.appendUint16(0); + eventActionDefinition5.appendUint16(2); + eventActionDefinition5.appendUint16(0); + eventActionDefinition5.appendUint16(3); + eventActionService.enableEventActionDefinitions(eventActionDefinition5); + std::cout << "\nStatus of position 0,1,2 should be 111:" << eventActionService + .eventActionDefinitionArray[0].enabled << eventActionService + .eventActionDefinitionArray[1].enabled << + eventActionService.eventActionDefinitionArray[2].enabled; + + Message eventActionDefinition4(19, 2, Message::TC, 1); + eventActionDefinition4.appendUint16(1); + eventActionDefinition4.appendUint16(0); + eventActionDefinition4.appendUint16(2); + + eventActionService.deleteEventActionDefinitions(eventActionDefinition4); + std::cout << "\nPositions 0,1 empty should be 11:" << (uint16_t) eventActionService + .eventActionDefinitionArray[0].empty + << (uint16_t) eventActionService.eventActionDefinitionArray[1].empty; + + Message eventActionDefinition6(19, 3, Message::TC, 1); + eventActionService.deleteAllEventActionDefinitions(eventActionDefinition6); + std::cout << "\nPositions 0,1 empty should be 1:" << (uint16_t) eventActionService + .eventActionDefinitionArray[0].empty; + + return 0; } diff --git a/test/MessageParser.cpp b/test/MessageParser.cpp index 25265d55137c85cdb7fbdbf1796cafb3d6d1f1f5..d06d7c2570cb9d036c7e1c01db5ba09a25fdf4bf 100644 --- a/test/MessageParser.cpp +++ b/test/MessageParser.cpp @@ -78,3 +78,7 @@ TEST_CASE("TC message parsing", "[MessageParser]") { CHECK(message.messageType == 31); CHECK(memcmp(message.data, "hello", 5) == 0); } + +TEST_CASE("TC data parsing into a message", "[MessageParser]") { + +} diff --git a/test/Services/EventActionService.cpp b/test/Services/EventActionService.cpp new file mode 100644 index 0000000000000000000000000000000000000000..f40de3fda9cc5aeab243d61ce786b5c991fb4651 --- /dev/null +++ b/test/Services/EventActionService.cpp @@ -0,0 +1,269 @@ +#include <catch2/catch.hpp> +#include <Services/EventActionService.hpp> +#include <Message.hpp> +#include "ServiceTests.hpp" +#include <etl/String.hpp> +#include <cstring> +#include <iostream> + +TEST_CASE("Add event-action definitions TC[19,1]", "[service][st09]") { + EventActionService eventActionService; + char checkstring[256]; + Message message(19, 1, Message::TC, 0); + message.appendEnum16(0); + message.appendEnum16(2); + String<64> data = "123"; + message.appendString(data); + + eventActionService.addEventActionDefinitions(message); + CHECK(eventActionService.eventActionDefinitionArray[0].empty == 0); + CHECK(eventActionService.eventActionDefinitionArray[0].applicationId == 0); + CHECK(eventActionService.eventActionDefinitionArray[0].eventDefinitionID == 2); + CHECK(eventActionService.eventActionDefinitionArray[0].enabled == 1); + CHECK(message.readEnum16() == 0); + CHECK(message.readEnum16() == 2); + message.readString(checkstring, 3); + CHECK(eventActionService.eventActionDefinitionArray[0].request.compare(data) == 0); + + Message message2(19, 1, Message::TC, 0); + message2.appendEnum16(1); + message2.appendEnum16(3); + data = "456"; + message2.appendString(data); + + eventActionService.addEventActionDefinitions(message2); + CHECK(eventActionService.eventActionDefinitionArray[1].empty == 0); + CHECK(eventActionService.eventActionDefinitionArray[1].applicationId == 1); + CHECK(eventActionService.eventActionDefinitionArray[1].eventDefinitionID == 3); + CHECK(eventActionService.eventActionDefinitionArray[1].enabled == 1); + + CHECK(message2.readEnum16() == 1); + CHECK(message2.readEnum16() == 3); + CHECK(eventActionService.eventActionDefinitionArray[1].request.compare(data) == 0); +} + +TEST_CASE("Delete event-action definitions TC[19,2]", "[service][st09]") { + EventActionService eventActionService; + Message message0(19, 1, Message::TC, 0); + message0.appendEnum16(1); + message0.appendEnum16(0); + String<64> data = "0"; + message0.appendString(data); + eventActionService.addEventActionDefinitions(message0); + Message message1(19, 1, Message::TC, 0); + message1.appendEnum16(1); + message1.appendEnum16(1); + data = "1"; + message1.appendString(data); + eventActionService.addEventActionDefinitions(message1); + Message message2(19, 1, Message::TC, 0); + message2.appendEnum16(1); + message2.appendEnum16(2); + data = "2"; + message2.appendString(data); + eventActionService.addEventActionDefinitions(message2); + Message message3(19, 1, Message::TC, 0); + message3.appendEnum16(1); + message3.appendEnum16(3); + data = "3"; + message3.appendString(data); + eventActionService.addEventActionDefinitions(message3); + Message message4(19, 1, Message::TC, 0); + message4.appendEnum16(1); + message4.appendEnum16(4); + data = "4"; + message4.appendString(data); + eventActionService.addEventActionDefinitions(message4); + + Message message(19, 2, Message::TC, 0); + message.appendUint16(2); + message.appendEnum16(1); + message.appendEnum16(4); + message.appendEnum16(1); + message.appendEnum16(2); + eventActionService.deleteEventActionDefinitions(message); + + CHECK(eventActionService.eventActionDefinitionArray[0].empty == 0); + CHECK(eventActionService.eventActionDefinitionArray[0].applicationId == 1); + CHECK(eventActionService.eventActionDefinitionArray[0].eventDefinitionID == 0); + CHECK(eventActionService.eventActionDefinitionArray[0].request.compare("0") == 0); + CHECK(eventActionService.eventActionDefinitionArray[0].enabled == 1); + + CHECK(eventActionService.eventActionDefinitionArray[1].empty == 0); + CHECK(eventActionService.eventActionDefinitionArray[1].applicationId == 1); + CHECK(eventActionService.eventActionDefinitionArray[1].eventDefinitionID == 1); + CHECK(eventActionService.eventActionDefinitionArray[1].request.compare("1") == 0); + CHECK(eventActionService.eventActionDefinitionArray[1].enabled == 1); + + CHECK(eventActionService.eventActionDefinitionArray[2].empty == 1); + CHECK(eventActionService.eventActionDefinitionArray[2].applicationId == 0); + CHECK(eventActionService.eventActionDefinitionArray[2].eventDefinitionID == 65535); + CHECK(eventActionService.eventActionDefinitionArray[2].request.compare("") == 0); + CHECK(eventActionService.eventActionDefinitionArray[2].enabled == 0); + + CHECK(eventActionService.eventActionDefinitionArray[3].empty == 0); + CHECK(eventActionService.eventActionDefinitionArray[3].applicationId == 1); + CHECK(eventActionService.eventActionDefinitionArray[3].eventDefinitionID == 3); + CHECK(eventActionService.eventActionDefinitionArray[3].request.compare("3") == 0); + CHECK(eventActionService.eventActionDefinitionArray[3].enabled == 1); + + CHECK(eventActionService.eventActionDefinitionArray[4].empty == 1); + CHECK(eventActionService.eventActionDefinitionArray[4].applicationId == 0); + CHECK(eventActionService.eventActionDefinitionArray[4].eventDefinitionID == 65535); + CHECK(eventActionService.eventActionDefinitionArray[4].request.compare("") == 0); + CHECK(eventActionService.eventActionDefinitionArray[4].enabled == 0); + +} + +TEST_CASE("Delete all event-action definitions TC[19,3]", "[service][st09]") { + EventActionService eventActionService; + Message message0(19, 1, Message::TC, 0); + message0.appendEnum16(1); + message0.appendEnum16(0); + String<64> data = "0"; + message0.appendString(data); + eventActionService.addEventActionDefinitions(message0); + Message message1(19, 1, Message::TC, 0); + message1.appendEnum16(1); + message1.appendEnum16(1); + data = "1"; + message1.appendString(data); + eventActionService.addEventActionDefinitions(message1); + Message message2(19, 1, Message::TC, 0); + message2.appendEnum16(1); + message2.appendEnum16(2); + data = "2"; + message2.appendString(data); + eventActionService.addEventActionDefinitions(message2); + Message message3(19, 1, Message::TC, 0); + message3.appendEnum16(1); + message3.appendEnum16(3); + data = "3"; + message3.appendString(data); + eventActionService.addEventActionDefinitions(message3); + Message message4(19, 1, Message::TC, 0); + message4.appendEnum16(1); + message4.appendEnum16(4); + data = "4"; + message4.appendString(data); + eventActionService.addEventActionDefinitions(message4); + + Message message(19, 3, Message::TC, 0); + eventActionService.deleteAllEventActionDefinitions(message); + + for (int i = 0; i < 256; i++){ + CHECK(eventActionService.eventActionDefinitionArray[i].empty == 1); + CHECK(eventActionService.eventActionDefinitionArray[i].applicationId == 0); + CHECK(eventActionService.eventActionDefinitionArray[i].eventDefinitionID == 65535); + CHECK(eventActionService.eventActionDefinitionArray[i].request.compare("") == 0); + } +} + +TEST_CASE("Enable event-action definitions TC[19,4]", "[service][st09]") { + EventActionService eventActionService; + Message message0(19, 1, Message::TC, 0); + message0.appendEnum16(1); + message0.appendEnum16(0); + String<64> data = "0"; + message0.appendString(data); + eventActionService.addEventActionDefinitions(message0); + Message message1(19, 1, Message::TC, 0); + message1.appendEnum16(1); + message1.appendEnum16(1); + data = "00"; + message1.appendString(data); + eventActionService.addEventActionDefinitions(message1); + Message message2(19, 4, Message::TC, 0); + message2.appendUint16(2); + message2.appendEnum16(1); + message2.appendEnum16(0); + message2.appendEnum16(1); + message2.appendEnum16(1); + eventActionService.enableEventActionDefinitions(message2); + CHECK(eventActionService.eventActionDefinitionArray[0].enabled == 1); + CHECK(eventActionService.eventActionDefinitionArray[1].enabled == 1); + +} + +TEST_CASE("Disable event-action definitions TC[19,5]", "[service][st09]") { + EventActionService eventActionService; + Message message0(19, 1, Message::TC, 0); + message0.appendEnum16(1); + message0.appendEnum16(0); + String<64> data = "0"; + message0.appendString(data); + eventActionService.addEventActionDefinitions(message0); + Message message1(19, 1, Message::TC, 0); + message1.appendEnum16(1); + message1.appendEnum16(0); + data = "00"; + message1.appendString(data); + eventActionService.addEventActionDefinitions(message1); + Message message2(19, 5, Message::TC, 0); + message2.appendUint16(1); + message2.appendEnum16(1); + message2.appendEnum16(0); + eventActionService.disableEventActionDefinitions(message2); + CHECK(eventActionService.eventActionDefinitionArray[0].enabled == 0); + CHECK(eventActionService.eventActionDefinitionArray[1].enabled == 0); +} + +TEST_CASE("Request event-action definition status TC[19,6]", "[service][st09]") { + EventActionService eventActionService; + Message message(19, 6, Message::TC, 0); + eventActionService.requestEventActionDefinitionStatus(message); + REQUIRE(ServiceTests::hasOneMessage()); + + Message report = ServiceTests::get(0); + CHECK(report.messageType == 7); +} + +TEST_CASE("Event-action status report TM[19,7]", "[service][st09]") { + EventActionService eventActionService; + Message message0(19, 1, Message::TC, 0); + message0.appendEnum16(1); + message0.appendEnum16(0); + String<64> data = "0"; + message0.appendString(data); + eventActionService.addEventActionDefinitions(message0); + Message message1(19, 1, Message::TC, 0); + message1.appendEnum16(1); + message1.appendEnum16(2); + data = "2"; + message1.appendString(data); + eventActionService.addEventActionDefinitions(message1); + Message message2(19, 5, Message::TC, 0); + message2.appendUint16(1); + message2.appendEnum16(1); + message2.appendEnum16(0); + eventActionService.disableEventActionDefinitions(message2); + eventActionService.eventActionStatusReport(); + REQUIRE(ServiceTests::hasOneMessage()); + + Message report = ServiceTests::get(0); + CHECK(report.readUint8() == 2); + CHECK(report.readEnum16() == 1); + CHECK(report.readEnum16() == 0); + CHECK(report.readUint8() == 0); + CHECK(report.readEnum16() == 1); + CHECK(report.readEnum16() == 2); + CHECK(report.readUint8() == 1); +} + +TEST_CASE("Enable event-action function TC[19,8]", "[service][st09]") { + EventActionService eventActionService; + Message message(19, 8, Message::TC, 0); + eventActionService.enableEventActionFunction(message); + CHECK(eventActionService.getEventActionFunctionStatus() == true); +} + +TEST_CASE("Disable event-action function TC[19,9]", "[service][st09]") { + EventActionService eventActionService; + Message message(19, 9, Message::TC, 0); + eventActionService.disableEventActionFunction(message); + CHECK(eventActionService.getEventActionFunctionStatus() == false); +} + +TEST_CASE("Execute a TC request", "[service][st09]"){ + +} diff --git a/test/Services/EventReportService.cpp b/test/Services/EventReportService.cpp index 0bf8133a30947c79942c360fc9f4db86c98c0143..ca90bee5d782856869384041d48f13d13054c694 100644 --- a/test/Services/EventReportService.cpp +++ b/test/Services/EventReportService.cpp @@ -5,7 +5,7 @@ #include <cstring> /* - * @todo Change the reinterpret_cast + * @todo: Change the reinterpret_cast */ TEST_CASE("Informative Event Report TM[5,1]", "[service][st05]") { EventReportService eventReportService;