summaryrefslogtreecommitdiffstats
path: root/extensions/openpower-pels
diff options
context:
space:
mode:
authorMatt Spinler <spinler@us.ibm.com>2019-12-12 10:35:01 -0600
committerMatt Spinler <spinler@us.ibm.com>2020-01-27 08:06:26 -0600
commit7d800a4e5d1305fa64ce02b99b0ec522bc454bbd (patch)
tree664b9dc6fed93d0637c7ee2f12d756f31b736d92 /extensions/openpower-pels
parent5342d9ad13453e2fe9558b12137cd9be2e220544 (diff)
downloadphosphor-logging-7d800a4e5d1305fa64ce02b99b0ec522bc454bbd.tar.gz
phosphor-logging-7d800a4e5d1305fa64ce02b99b0ec522bc454bbd.zip
PEL: On new PEL, send to host if necessary
When a new PEL comes in, send it to the host now if the host is up and the class is currently idle. The PLDM command will be dispatched in a standalone function called from the event loop so that this function, which may be part of the 'Create new log' D-Bus method response, can return first. Also added testcases to start verifying these paths now that there is a full mock of the HostInterface class. Signed-off-by: Matt Spinler <spinler@us.ibm.com> Change-Id: Ib30a99cc61be9205122287ba310bc315d762e863
Diffstat (limited to 'extensions/openpower-pels')
-rw-r--r--extensions/openpower-pels/host_notifier.cpp36
-rw-r--r--extensions/openpower-pels/host_notifier.hpp26
2 files changed, 61 insertions, 1 deletions
diff --git a/extensions/openpower-pels/host_notifier.cpp b/extensions/openpower-pels/host_notifier.cpp
index 8fe6955..f2d951f 100644
--- a/extensions/openpower-pels/host_notifier.cpp
+++ b/extensions/openpower-pels/host_notifier.cpp
@@ -155,7 +155,41 @@ void HostNotifier::newLogCallback(const PEL& pel)
_pelQueue.push_back(pel.id());
- // TODO: Check if a send is needed now
+ if (!_dataIface.isHostUp())
+ {
+ return;
+ }
+
+ // Dispatch a command now if there isn't currently a command
+ // in progress and this is the first log in the queue or it
+ // previously gave up from a hard failure.
+ auto inProgress = (_inProgressPEL != 0) || _hostIface->cmdInProgress() ||
+ _retryTimer.isEnabled();
+
+ auto firstPEL = _pelQueue.size() == 1;
+ auto gaveUp = _retryCount >= maxRetryAttempts;
+
+ if (!inProgress && (firstPEL || gaveUp))
+ {
+ _retryCount = 0;
+
+ // Send a log, but from the event loop, not from here.
+ scheduleDispatch();
+ }
+}
+
+void HostNotifier::scheduleDispatch()
+{
+ _dispatcher = std::make_unique<sdeventplus::source::Defer>(
+ _hostIface->getEvent(), std::bind(std::mem_fn(&HostNotifier::dispatch),
+ this, std::placeholders::_1));
+}
+
+void HostNotifier::dispatch(sdeventplus::source::EventBase& source)
+{
+ _dispatcher.reset();
+
+ doNewLogNotify();
}
void HostNotifier::doNewLogNotify()
diff --git a/extensions/openpower-pels/host_notifier.hpp b/extensions/openpower-pels/host_notifier.hpp
index 127eb03..3e50c83 100644
--- a/extensions/openpower-pels/host_notifier.hpp
+++ b/extensions/openpower-pels/host_notifier.hpp
@@ -6,6 +6,7 @@
#include <deque>
#include <sdeventplus/clock.hpp>
+#include <sdeventplus/source/event.hpp>
#include <sdeventplus/utility/timer.hpp>
namespace openpower::pels
@@ -86,6 +87,10 @@ class HostNotifier
* @brief This function gets called by the Repository class
* when a new PEL is added to it.
*
+ * This function puts the PEL on the queue to be sent up if it
+ * needs it, and possibly dispatch the send if the conditions call
+ * for it.
+ *
* @param[in] pel - The new PEL
*/
void newLogCallback(const PEL& pel);
@@ -108,6 +113,20 @@ class HostNotifier
void doNewLogNotify();
/**
+ * @brief Creates the event object to handle sending the PLDM
+ * command from the event loop.
+ */
+ void scheduleDispatch();
+
+ /**
+ * @brief Kicks off the PLDM send, but called from the event
+ * loop.
+ *
+ * @param[in] source - The event source object
+ */
+ void dispatch(sdeventplus::source::EventBase& source);
+
+ /**
* @brief Called when the host changes state.
*
* If the new state is host up and there are PELs to send, it
@@ -192,6 +211,13 @@ class HostNotifier
* @brief The command retry timer.
*/
sdeventplus::utility::Timer<sdeventplus::ClockId::Monotonic> _retryTimer;
+
+ /**
+ * @brief The object used to dispatch a new PEL send from the
+ * event loop, so the calling function can be returned from
+ * first.
+ */
+ std::unique_ptr<sdeventplus::source::Defer> _dispatcher;
};
} // namespace openpower::pels
OpenPOWER on IntegriCloud