/** * @file JAConditionalSignalUpdateGAM.cpp * @brief Source file for class JAConditionalSignalUpdateGAM * @date Jan, 2019 * @author rhari * * @copyright Copyright 2015 F4E | European Joint Undertaking for ITER and * the Development of Fusion Energy ('Fusion for Energy'). * Licensed under the EUPL, Version 1.1 or - as soon they will be approved * by the European Commission - subsequent versions of the EUPL (the "Licence") * You may not use this work except in compliance with the Licence. * You may obtain a copy of the Licence at: http://ec.europa.eu/idabc/eupl * * @warning Unless required by applicable law or agreed to in writing, * software distributed under the Licence is distributed on an "AS IS" * basis, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express * or implied. See the Licence permissions and limitations under the Licence. * @details This source file contains the definition of all the methods for * the class JAConditionalSignalUpdateGAM (public, protected, and private). Be aware that some * methods, such as those inline could be defined on the header file, instead. */ /*---------------------------------------------------------------------------*/ /* Standard header includes */ /*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/ /* Project header includes */ /*---------------------------------------------------------------------------*/ #include "AdvancedErrorManagement.h" #include "Architecture/x86_gcc/CompilerTypes.h" #include "ErrorType.h" #include "JAConditionalSignalUpdateGAM.h" #include "TypeDescriptor.h" /*---------------------------------------------------------------------------*/ /* Static definitions */ /*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/ /* Method definitions */ /*---------------------------------------------------------------------------*/ bool parse_comparator(const MARTe::StreamString &str, JAConditionalSignalUpdateGAM::ComparisonMode &op) { if (str == "EQUALS") { op = JAConditionalSignalUpdateGAM::Equals; return true; } if (str == "NOT") { op = JAConditionalSignalUpdateGAM::Not; return true; } if (str == "GREATER") { op = JAConditionalSignalUpdateGAM::Greater; return true; } if (str == "EQUALS_OR_GREATER") { op = JAConditionalSignalUpdateGAM::EqualsOrGreater; return true; } if (str == "LESS") { op = JAConditionalSignalUpdateGAM::Less; return true; } if (str == "EQUALS_OR_LESS") { op = JAConditionalSignalUpdateGAM::EqualsOrLess; return true; } return false; } JAConditionalSignalUpdateGAM::JAConditionalSignalUpdateGAM() { inputSignals = NULL_PTR(void **); inputSignalTypes = NULL_PTR(MARTe::TypeDescriptor *); comparators = NULL_PTR(comparator_t *); outputSignals = NULL_PTR(MARTe::uint32 **); outputs = NULL_PTR(output_t *); needsReset = false; operation = And; } JAConditionalSignalUpdateGAM::~JAConditionalSignalUpdateGAM() { if (outputSignals != NULL_PTR(MARTe::uint32 **)) { delete[] outputSignals; } if (inputSignals != NULL_PTR(void **)) { delete[] inputSignals; } if (inputSignalTypes != NULL_PTR(MARTe::TypeDescriptor *)) { delete[] inputSignalTypes; } if (outputs != NULL_PTR(output_t *)) { delete[] outputs; } if (comparators != NULL_PTR(comparator_t *)) { delete[] comparators; } } bool JAConditionalSignalUpdateGAM::Initialise(MARTe::StructuredDataI &data) { using namespace MARTe; bool ok = GAM::Initialise(data); if (ok) { MARTe::StreamString operationStr; if (data.Read("Operation", operationStr)) { if (operationStr == "AND") { operation = And; } else if (operationStr == "OR") { operation = Or; } else if (operationStr == "NOR") { operation = Nor; } else if (operationStr == "XOR") { operation = Xor; } else { ok = false; REPORT_ERROR(ErrorManagement::ParametersError, "Operation %s is not defined", operationStr.Buffer()); } } } if (ok) { ok = data.MoveRelative("InputSignals"); uint32 level = 0; if (ok) { level++; uint32 n_inputs = data.GetNumberOfChildren(); comparators = new comparator_t[n_inputs]; StreamString buffer; TypeDescriptor td; for (uint32 i = 0; ok && i < n_inputs; i++) { ok = data.MoveToChild(i); if (!ok) { REPORT_ERROR(ErrorManagement::ParametersError, "Impossible to move to InputSignals[%lu]", i); break; } level++; ok = data.Read("Type", buffer); if (!ok) { REPORT_ERROR(ErrorManagement::ParametersError, "Missing mandatory field Type from InputSignals[%lu]", i); break; } td = TypeDescriptor::GetTypeDescriptorFromTypeName(buffer.Buffer()); ok = (td == UnsignedInteger8Bit) || (td == UnsignedInteger16Bit) || (td == UnsignedInteger32Bit); if (!ok) { REPORT_ERROR(ErrorManagement::ParametersError, "Wrong value for field Type from InputSignals[%lu]", i); break; } ok = data.Read("Comparator", buffer); if (!ok) { REPORT_ERROR( ErrorManagement::ParametersError, "Missing mandatory field Comparator from InputSignals[%lu]", i); break; } ok = parse_comparator(buffer, comparators[i].comparator); if (!ok) { REPORT_ERROR(ErrorManagement::ParametersError, "Non Valid Comparator `%s` from InputSignals[%lu]", buffer, i); break; } ok = data.Read("Value", comparators[i].value); if (!ok) { REPORT_ERROR( ErrorManagement::ParametersError, "Missing field Value (expecting int) from InputSignals[%lu]", i); break; } if (data.MoveToAncestor(1)) { level--; } else { ok = false; } } data.MoveToAncestor(level); } else { REPORT_ERROR(ErrorManagement::ParametersError, "Impossible to move to InputSignals"); } } if (ok) { ok = data.MoveRelative("OutputSignals"); uint32 level = 0; if (ok) { level++; uint32 n_outputs = data.GetNumberOfChildren(); outputs = new output_t[n_outputs]; for (uint32 i = 0; ok && i < n_outputs; i++) { ok = data.MoveToChild(i); if (!ok) { REPORT_ERROR(ErrorManagement::ParametersError, "Impossible to move to InputSignals[%lu]", i); break; } level++; ok = data.Read("DefaultValue", outputs[i].defaultValue); if (!ok) { REPORT_ERROR(ErrorManagement::ParametersError, "Impossible to read field DefaultValue for output %lu", i); break; } ok = data.Read("Value", outputs[i].value); if (!ok) { REPORT_ERROR(ErrorManagement::ParametersError, "Impossible to read field Value for output %lu", i); break; } ok = data.MoveToAncestor(1); if (ok) { level--; } } data.MoveToAncestor(level); } else { REPORT_ERROR(ErrorManagement::ParametersError, "Impossible to move to OutputSignals"); } } return ok; } bool JAConditionalSignalUpdateGAM::Setup() { using namespace MARTe; bool ok = numberOfInputSignals > 0; if (ok) { inputSignals = new void *[numberOfInputSignals]; uint32 i; for (uint32 i = 0u; i < numberOfOutputSignals; i++) { inputSignals[i] = GetInputSignalMemory(i); } } else { REPORT_ERROR(ErrorManagement::ParametersError, "Number of input signals shall be greater then 0 "); } if (ok) { ok = numberOfOutputSignals > 0u; if (ok) { outputSignals = new uint32 *[numberOfOutputSignals]; for (uint32 i = 0u; i < numberOfOutputSignals; i++) { outputSignals[i] = reinterpret_cast(GetOutputSignalMemory(i)); } } else { REPORT_ERROR(ErrorManagement::ParametersError, "At least one output signal shall be defined"); } } return ok; } bool JAConditionalSignalUpdateGAM::PrepareNextState( const MARTe::char8 *const currentStateName, const MARTe::char8 *const nextStateName) { needsReset = false; return true; } bool accumulate(JAConditionalSignalUpdateGAM::OperationMode mode, bool next, bool current) { switch (mode) { case JAConditionalSignalUpdateGAM::Or: return next || current; case JAConditionalSignalUpdateGAM::And: return next && current; case JAConditionalSignalUpdateGAM::Nor: return !(next || current); case JAConditionalSignalUpdateGAM::Xor: return (!next != !current); } return false; } bool JAConditionalSignalUpdateGAM::Execute() { if (!needsReset) { bool state = Compare(0); for (MARTe::uint32 i = 1; i < numberOfInputSignals; i++) { state = accumulate(operation, Compare(i), state); } if (state) { needsReset = true; MARTe::uint32 i; for (i = 0u; i < numberOfOutputSignals; ++i) { *outputSignals[i] = outputs[i].value; } } else { MARTe::uint32 i; for (i = 0u; i < numberOfOutputSignals; ++i) { *outputSignals[i] = outputs[i].defaultValue; } } } return true; } bool JAConditionalSignalUpdateGAM::Compare(MARTe::uint32 index) { if (inputSignalTypes[index] == MARTe::UnsignedInteger32Bit) { return Compare(index); } return Compare(index); } CLASS_REGISTER(JAConditionalSignalUpdateGAM, "1.0")