F´ Flight Software - C/C++ Documentation devel
A framework for building embedded system applications to NASA flight quality standards.
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
HealthComponentImpl.cpp
Go to the documentation of this file.
1// ======================================================================
2// \title Health.hpp
3// \author Tim
4// \brief hpp file for Health component implementation class
5//
6// \copyright
7// Copyright 2009-2015, by the California Institute of Technology.
8// ALL RIGHTS RESERVED. United States Government Sponsorship
9// acknowledged.
10//
11// ======================================================================
12
14#include <FpConfig.hpp>
15#include <Fw/Types/Assert.hpp>
16
17namespace Svc {
18
19 // ----------------------------------------------------------------------
20 // Construction, initialization, and destruction
21 // ----------------------------------------------------------------------
22
23 HealthImpl::HealthImpl(const char * const compName) :
24 HealthComponentBase(compName),
25 m_numPingEntries(0),
26 m_key(0),
27 m_watchDogCode(0),
28 m_warnings(0),
29 m_enabled(Fw::Enabled::ENABLED),
30 queue_depth(0) {
31 // clear tracker by disabling pings
32 for (NATIVE_UINT_TYPE entry = 0;
33 entry < FW_NUM_ARRAY_ELEMENTS(this->m_pingTrackerEntries);
34 entry++) {
35 this->m_pingTrackerEntries[entry].enabled = Fw::Enabled::DISABLED;
36 }
37 }
38
39 void HealthImpl::init(const NATIVE_INT_TYPE queueDepth, const NATIVE_INT_TYPE instance) {
40 HealthComponentBase::init(queueDepth, instance);
41 this->queue_depth = queueDepth;
42
43 }
44
45 void HealthImpl::setPingEntries(PingEntry* pingEntries, NATIVE_INT_TYPE numPingEntries, U32 watchDogCode) {
46
47 FW_ASSERT(pingEntries);
48 // make sure not asking for more pings than ports
49 FW_ASSERT(numPingEntries <= NUM_PINGSEND_OUTPUT_PORTS);
50
51 this->m_numPingEntries = numPingEntries;
52 this->m_watchDogCode = watchDogCode;
53
54 // copy entries to private data
55 for (NATIVE_INT_TYPE entry = 0; entry < numPingEntries; entry++) {
56 FW_ASSERT(pingEntries[entry].warnCycles <= pingEntries[entry].fatalCycles, pingEntries[entry].warnCycles, pingEntries[entry].fatalCycles);
57 this->m_pingTrackerEntries[entry].entry = pingEntries[entry];
58 this->m_pingTrackerEntries[entry].cycleCount = 0;
59 this->m_pingTrackerEntries[entry].enabled = Fw::Enabled::ENABLED;
60 this->m_pingTrackerEntries[entry].key = 0;
61 }
62 }
63
67
68 // ----------------------------------------------------------------------
69 // Handler implementations for user-defined typed input ports
70 // ----------------------------------------------------------------------
71
72 void HealthImpl::PingReturn_handler(const NATIVE_INT_TYPE portNum, U32 key) {
73 // verify the key value
74 if (key != this->m_pingTrackerEntries[portNum].key) {
75 Fw::LogStringArg _arg = this->m_pingTrackerEntries[portNum].entry.entryName;
76 this->log_FATAL_HLTH_PING_WRONG_KEY(_arg,key);
77 } else {
78 // reset the counter and clear the key
79 this->m_pingTrackerEntries[portNum].cycleCount = 0;
80 this->m_pingTrackerEntries[portNum].key = 0;
81 }
82
83 }
84
85 void HealthImpl::Run_handler(const NATIVE_INT_TYPE portNum, NATIVE_UINT_TYPE context) {
86 //dispatch messages
87 for (NATIVE_UINT_TYPE i = 0; i < this->queue_depth; i++) {
88 MsgDispatchStatus stat = this->doDispatch();
89 if (MSG_DISPATCH_EMPTY == stat) {
90 break;
91 }
93 }
94
95 if (this->m_enabled == Fw::Enabled::ENABLED) {
96 // cycle through ping table, pinging ports that are not awaiting a reply
97 // for ports that are awaiting a reply, decrement their counters
98 // and check for violations
99
100 for (NATIVE_UINT_TYPE entry = 0; entry < this->m_numPingEntries; entry++) {
101 if (Fw::Enabled::ENABLED == this->m_pingTrackerEntries[entry].enabled) {
102 // If clear entry
103 if (0 == this->m_pingTrackerEntries[entry].cycleCount) {
104 // start a ping
105 this->m_pingTrackerEntries[entry].key = this->m_key;
106 // send ping
107 this->PingSend_out(entry, this->m_pingTrackerEntries[entry].key);
108 // increment key
109 this->m_key++;
110 // increment cycles for the entry
111 this->m_pingTrackerEntries[entry].cycleCount++;
112 } else {
113 // check to see if it is at warning threshold
114 if (this->m_pingTrackerEntries[entry].cycleCount ==
115 this->m_pingTrackerEntries[entry].entry.warnCycles) {
116 Fw::LogStringArg _arg = this->m_pingTrackerEntries[entry].entry.entryName;
118 this->tlmWrite_PingLateWarnings(++this->m_warnings);
119 } else {
120 // check for FATAL timeout value
121 if (this->m_pingTrackerEntries[entry].entry.fatalCycles ==
122 this->m_pingTrackerEntries[entry].cycleCount) {
123 Fw::LogStringArg _arg = this->m_pingTrackerEntries[entry].entry.entryName;
124 this->log_FATAL_HLTH_PING_LATE(_arg);
125 }
126 } // if at warning or fatal threshold
127
128 this->m_pingTrackerEntries[entry].cycleCount++;
129 } // if clear entry
130 } // if entry has ping enabled
131 } // for each entry
132
133 // do other specialized platform checks (e.g. VxWorks suspended tasks)
134 this->doOtherChecks();
135
136 } // If health checking is enabled
137
138 // stroke watchdog.
140 this->WdogStroke_out(0,this->m_watchDogCode);
141 }
142 }
143
144 // ----------------------------------------------------------------------
145 // Command handler implementations
146 // ----------------------------------------------------------------------
147
148 void HealthImpl::HLTH_ENABLE_cmdHandler(const FwOpcodeType opCode, U32 cmdSeq, Fw::Enabled enable) {
149 this->m_enabled = enable;
151 if (enable == Fw::Enabled::ENABLED) {
152 isEnabled = Fw::Enabled::ENABLED;
153 }
154 this->log_ACTIVITY_HI_HLTH_CHECK_ENABLE(isEnabled);
155 this->cmdResponse_out(opCode,cmdSeq,Fw::CmdResponse::OK);
156 }
157
158
159 void HealthImpl::HLTH_PING_ENABLE_cmdHandler(const FwOpcodeType opCode, U32 cmdSeq, const Fw::CmdStringArg& entry, Fw::Enabled enable) {
160 // check to see if entry is in range
161 NATIVE_INT_TYPE entryIndex = this->findEntry(entry);
162
163 if (-1 == entryIndex) {
165 return;
166 }
167
168 this->m_pingTrackerEntries[entryIndex].enabled = enable.e;
170 if (enable == Fw::Enabled::ENABLED) {
171 isEnabled = Fw::Enabled::ENABLED;
172 }
174 arg = entry;
175 this->log_ACTIVITY_HI_HLTH_CHECK_PING(isEnabled,arg);
176 this->cmdResponse_out(opCode,cmdSeq,Fw::CmdResponse::OK);
177 }
178
179 void HealthImpl::HLTH_CHNG_PING_cmdHandler(const FwOpcodeType opCode, U32 cmdSeq, const Fw::CmdStringArg& entry, U32 warningValue, U32 fatalValue) {
180 // check to see if entry is in range
181 NATIVE_INT_TYPE entryIndex = this->findEntry(entry);
182 if (-1 == entryIndex) {
184 return;
185 }
186
187 //check to see if warningValue less than or equal to fatalValue
188 if (warningValue > fatalValue) {
190 arg = entry;
191 this->log_WARNING_HI_HLTH_PING_INVALID_VALUES(arg,warningValue,fatalValue);
193 return;
194 }
195
196 this->m_pingTrackerEntries[entryIndex].entry.warnCycles = warningValue;
197 this->m_pingTrackerEntries[entryIndex].entry.fatalCycles = fatalValue;
198 Fw::LogStringArg arg = entry;
199 this->log_ACTIVITY_HI_HLTH_PING_UPDATED(arg,warningValue,fatalValue);
200 this->cmdResponse_out(opCode,cmdSeq,Fw::CmdResponse::OK);
201 }
202
203 NATIVE_INT_TYPE HealthImpl::findEntry(const Fw::CmdStringArg& entry) {
204
205 // walk through entries
206 for (NATIVE_UINT_TYPE tableEntry = 0; tableEntry < NUM_PINGSEND_OUTPUT_PORTS; tableEntry++) {
207 if (entry == this->m_pingTrackerEntries[tableEntry].entry.entryName) {
208 return tableEntry;
209 }
210 }
211 Fw::LogStringArg arg = entry;
213
214 return -1;
215 }
216
217
218
219} // end namespace Svc
#define FW_ASSERT(...)
Definition Assert.hpp:14
PlatformIntType NATIVE_INT_TYPE
Definition BasicTypes.h:51
#define FW_NUM_ARRAY_ELEMENTS(a)
number of elements in an array
Definition BasicTypes.h:66
PlatformUIntType NATIVE_UINT_TYPE
Definition BasicTypes.h:52
U32 FwOpcodeType
Definition FpConfig.h:56
C++-compatible configuration header for fprime configuration.
@ VALIDATION_ERROR
Command failed validation.
@ OK
Command successfully executed.
Enabled and disabled states.
T e
The raw enum value.
@ ENABLED
Enabled state.
@ DISABLED
Disabled state.
void init()
Object initializer.
Definition ObjBase.cpp:27
@ MSG_DISPATCH_EMPTY
No more messages in the queue.
@ MSG_DISPATCH_OK
Dispatch was normal.
Auto-generated base for Health component.
void tlmWrite_PingLateWarnings(U32 arg, Fw::Time _tlmTime=Fw::Time())
void log_ACTIVITY_HI_HLTH_CHECK_PING(Fw::Enabled enabled, const Fw::LogStringArg &entry)
virtual MsgDispatchStatus doDispatch()
Called in the message loop to dispatch a message from the queue.
void log_FATAL_HLTH_PING_WRONG_KEY(const Fw::LogStringArg &entry, U32 badKey)
bool isConnected_WdogStroke_OutputPort(NATIVE_INT_TYPE portNum)
void log_FATAL_HLTH_PING_LATE(const Fw::LogStringArg &entry)
void log_WARNING_LO_HLTH_CHECK_LOOKUP_ERROR(const Fw::LogStringArg &entry)
void log_WARNING_HI_HLTH_PING_WARN(const Fw::LogStringArg &entry)
void log_ACTIVITY_HI_HLTH_CHECK_ENABLE(Fw::Enabled enabled)
void PingSend_out(NATIVE_INT_TYPE portNum, U32 key)
Invoke output port PingSend.
void log_WARNING_HI_HLTH_PING_INVALID_VALUES(const Fw::LogStringArg &entry, U32 warn, U32 fatal)
void cmdResponse_out(FwOpcodeType opCode, U32 cmdSeq, Fw::CmdResponse response)
Emit command response.
void log_ACTIVITY_HI_HLTH_PING_UPDATED(const Fw::LogStringArg &entry, U32 warn, U32 fatal)
void WdogStroke_out(NATIVE_INT_TYPE portNum, U32 code)
Invoke output port WdogStroke.
virtual void doOtherChecks()
additional checks function
~HealthImpl()
Component destructor.
void setPingEntries(PingEntry *pingEntries, NATIVE_INT_TYPE numPingEntries, U32 watchDogCode)
Set ping entry tables.
HealthImpl(const char *const compName)
HealthImpl constructor.
struct for ping entry
Fw::String entryName
the name of the entry
NATIVE_UINT_TYPE warnCycles
number of cycles before WARNING
NATIVE_UINT_TYPE fatalCycles
number of cycles before FATAL