diff --git a/meson.build b/meson.build
index 8e48b26..b22bec4 100644
--- a/meson.build
+++ b/meson.build
@@ -70,6 +70,8 @@
   libphal_dep = cmplr.find_library('phal')
 endif
 
+libpldm_dep = dependency('libpldm')
+
 pthread = declare_dependency(link_args : '-pthread')
 lrt = declare_dependency(link_args : '-lrt')
 
diff --git a/util/meson.build b/util/meson.build
index 7eb6d91..4b107d8 100644
--- a/util/meson.build
+++ b/util/meson.build
@@ -6,6 +6,7 @@
     'ffdc_file.cpp',
     'pdbg.cpp',
     'pdbg-no-sim.cpp',
+    'pldm.cpp',
     'temporary_file.cpp',
 )
 
@@ -13,6 +14,7 @@
 util_deps = [
     libhei_dep,
     libpdbg_dep,
+    libpldm_dep,
     phosphor_logging_dep,
 ]
 
diff --git a/util/pldm.cpp b/util/pldm.cpp
new file mode 100644
index 0000000..cdf1cfd
--- /dev/null
+++ b/util/pldm.cpp
@@ -0,0 +1,396 @@
+#include <libpldm/platform.h>
+#include <libpldm/pldm.h>
+#include <libpldm/state_set_oem_ibm.h>
+
+#include <util/dbus.hpp>
+#include <util/trace.hpp>
+
+namespace util
+{
+namespace pldm
+{
+/** @brief Send PLDM request
+ *
+ * @param[in] request - the request data
+ * @param[in] mcptEid - the mctp endpoint ID
+ * @param[out] pldmFd - pldm socket file descriptor
+ *
+ * @pre a mctp instance must have been
+ * @return true if send is successful false otherwise
+ */
+bool sendPldm(const std::vector<uint8_t>& request, uint8_t mctpEid, int& pldmFd)
+{
+    // connect to socket
+    pldmFd = pldm_open();
+    if (-1 == pldmFd)
+    {
+        trace::err("failed to connect to pldm");
+        return false;
+    }
+
+    // send PLDM request
+    auto pldmRc = pldm_send(mctpEid, pldmFd, request.data(), request.size());
+
+    trace::inf("sent pldm request");
+
+    return pldmRc == PLDM_REQUESTER_SUCCESS ? true : false;
+}
+
+/** @brief Prepare a request for SetStateEffecterStates
+ *
+ *  @param[in] effecterId - the effecter ID
+ *  @param[in] effecterCount - composite effecter count
+ *  @param[in] stateIdPos - position of the state set
+ *  @param[in] stateSetValue - the value to set the state
+ *  @param[in] mcptEid - the MCTP endpoint ID
+ *
+ *  @return PLDM request message to be sent to host, empty message on error
+ */
+std::vector<uint8_t> prepareSetEffecterReq(uint16_t effecterId,
+                                           uint8_t effecterCount,
+                                           uint8_t stateIdPos,
+                                           uint8_t stateSetValue,
+                                           uint8_t mctpEid)
+{
+    // get mctp instance associated with the endpoint ID
+    uint8_t mctpInstance;
+    if (!util::dbus::getMctpInstance(mctpInstance, mctpEid))
+    {
+        return std::vector<uint8_t>();
+    }
+
+    // form the request message
+    std::vector<uint8_t> request(
+        sizeof(pldm_msg_hdr) + sizeof(effecterId) + sizeof(effecterCount) +
+        (effecterCount * sizeof(set_effecter_state_field)));
+
+    // encode the state data with the change we want to elicit
+    std::vector<set_effecter_state_field> stateField;
+    for (uint8_t effecterPos = 0; effecterPos < effecterCount; effecterPos++)
+    {
+        if (effecterPos == stateIdPos)
+        {
+            stateField.emplace_back(
+                set_effecter_state_field{PLDM_REQUEST_SET, stateSetValue});
+        }
+        else
+        {
+            stateField.emplace_back(
+                set_effecter_state_field{PLDM_NO_CHANGE, 0});
+        }
+    }
+
+    // encode the message with state data
+    auto requestMsg = reinterpret_cast<pldm_msg*>(request.data());
+    auto rc         = encode_set_state_effecter_states_req(
+        mctpInstance, effecterId, effecterCount, stateField.data(), requestMsg);
+
+    if (rc != PLDM_SUCCESS)
+    {
+        trace::err("encode set effecter states request failed");
+        request.clear();
+    }
+
+    return request;
+}
+
+/** @brief Return map of sensor ID to SBE instance
+ *
+ *  @param[in] stateSetId - the state set ID of interest
+ *  @param[out] sensorInstanceMap - map of sensor to SBE instance
+ *  @param[out] sensorOffset - position of sensor with state set ID within map
+ *
+ *  @return true if sensor info is available false otherwise
+ */
+bool fetchSensorInfo(uint16_t stateSetId,
+                     std::map<uint16_t, unsigned int>& sensorInstanceMap,
+                     uint8_t& sensorOffset)
+{
+    // get state sensor PDRs
+    std::vector<std::vector<uint8_t>> pdrs{};
+    if (!util::dbus::getStateSensorPdrs(pdrs, stateSetId))
+    {
+        return false;
+    }
+
+    // check for any PDRs available
+    if (!pdrs.size())
+    {
+        trace::err("state sensor PDRs not present");
+        return false;
+    }
+
+    // find the offset of specified sensor withing PDRs
+    bool offsetFound = false;
+    auto stateSensorPDR =
+        reinterpret_cast<const pldm_state_sensor_pdr*>(pdrs.front().data());
+    auto possibleStatesPtr = stateSensorPDR->possible_states;
+
+    for (auto offset = 0; offset < stateSensorPDR->composite_sensor_count;
+         offset++)
+    {
+        auto possibleStates =
+            reinterpret_cast<const state_sensor_possible_states*>(
+                possibleStatesPtr);
+
+        if (possibleStates->state_set_id == stateSetId)
+        {
+            sensorOffset = offset;
+            offsetFound  = true;
+            break;
+        }
+        possibleStatesPtr += sizeof(possibleStates->state_set_id) +
+                             sizeof(possibleStates->possible_states_size) +
+                             possibleStates->possible_states_size;
+    }
+
+    if (!offsetFound)
+    {
+        trace::err("state sensor not found");
+        return false;
+    }
+
+    // map sensor ID to equivelent 16 bit value
+    std::map<uint32_t, uint16_t> entityInstMap{};
+    for (auto& pdr : pdrs)
+    {
+        auto pdrPtr =
+            reinterpret_cast<const pldm_state_sensor_pdr*>(pdr.data());
+        uint32_t key = pdrPtr->sensor_id;
+        entityInstMap.emplace(key, static_cast<uint16_t>(pdrPtr->sensor_id));
+    }
+
+    // map sensor ID to zero based SBE instance
+    unsigned int position = 0;
+    for (auto const& pair : entityInstMap)
+    {
+        sensorInstanceMap.emplace(pair.second, position);
+        position++;
+    }
+
+    return true;
+}
+
+/** @brief Return map of SBE instance to effecter ID
+ *
+ *  @param[in] stateSetId - the state set ID of interest
+ *  @param[out] instanceToEffecterMap - map of sbe instance to effecter ID
+ *  @param[out] effecterCount - composite effecter count
+ *  @param[out] stateIdPos - position of effecter with state set ID within map
+ *
+ *  @return true if effector info is available false otherwise
+ */
+bool fetchEffecterInfo(uint16_t stateSetId,
+                       std::map<unsigned int, uint16_t>& instanceToEffecterMap,
+                       uint8_t& effecterCount, uint8_t& stateIdPos)
+{
+    // get state effecter PDRs
+    std::vector<std::vector<uint8_t>> pdrs{};
+    if (!util::dbus::getStateEffecterPdrs(pdrs, stateSetId))
+    {
+        return false;
+    }
+
+    // check for any PDRs available
+    if (!pdrs.size())
+    {
+        trace::err("state effecter PDRs not present");
+        return false;
+    }
+
+    // find the offset of specified effector within PDRs
+    bool offsetFound = false;
+    auto stateEffecterPDR =
+        reinterpret_cast<const pldm_state_effecter_pdr*>(pdrs.front().data());
+    auto possibleStatesPtr = stateEffecterPDR->possible_states;
+
+    for (auto offset = 0; offset < stateEffecterPDR->composite_effecter_count;
+         offset++)
+    {
+        auto possibleStates =
+            reinterpret_cast<const state_effecter_possible_states*>(
+                possibleStatesPtr);
+
+        if (possibleStates->state_set_id == stateSetId)
+        {
+            stateIdPos    = offset;
+            effecterCount = stateEffecterPDR->composite_effecter_count;
+            offsetFound   = true;
+            break;
+        }
+        possibleStatesPtr += sizeof(possibleStates->state_set_id) +
+                             sizeof(possibleStates->possible_states_size) +
+                             possibleStates->possible_states_size;
+    }
+
+    if (!offsetFound)
+    {
+        trace::err("state set effecter not found");
+        return false;
+    }
+
+    // map effecter ID to equivelent 16 bit value
+    std::map<uint32_t, uint16_t> entityInstMap{};
+    for (auto& pdr : pdrs)
+    {
+        auto pdrPtr =
+            reinterpret_cast<const pldm_state_effecter_pdr*>(pdr.data());
+        uint32_t key = pdrPtr->effecter_id;
+        entityInstMap.emplace(key, static_cast<uint16_t>(pdrPtr->effecter_id));
+    }
+
+    // map zero based SBE instance to effecter ID
+    unsigned int position = 0;
+    for (auto const& pair : entityInstMap)
+    {
+        instanceToEffecterMap.emplace(position, pair.second);
+        position++;
+    }
+
+    return true;
+}
+
+/**  @brief Reset SBE using HBRT PLDM interface */
+bool hresetSbe(unsigned int sbeInstance)
+{
+    trace::inf("requesting sbe hreset");
+
+    // get effecter info
+    std::map<unsigned int, uint16_t> sbeInstanceToEffecter;
+    uint8_t SBEEffecterCount            = 0;
+    uint8_t sbeMaintenanceStatePosition = 0;
+
+    if (!fetchEffecterInfo(PLDM_OEM_IBM_SBE_MAINTENANCE_STATE,
+                           sbeInstanceToEffecter, SBEEffecterCount,
+                           sbeMaintenanceStatePosition))
+    {
+        return false;
+    }
+
+    // find the state effecter ID for the given SBE instance
+    auto effecterEntry = sbeInstanceToEffecter.find(sbeInstance);
+    if (effecterEntry == sbeInstanceToEffecter.end())
+    {
+        trace::err("failed to find effecter for SBE");
+        return false;
+    }
+
+    // create request to HRESET the SBE
+    constexpr uint8_t hbrtMctpEid = 10; // HBRT MCTP EID
+
+    auto request = prepareSetEffecterReq(
+        effecterEntry->second, SBEEffecterCount, sbeMaintenanceStatePosition,
+        SBE_RETRY_REQUIRED, hbrtMctpEid);
+
+    if (request.empty())
+    {
+        trace::err("HRESET effecter request empty");
+        return false;
+    }
+
+    // get sensor info for validating sensor change
+    std::map<uint16_t, unsigned int> sensorToSbeInstance;
+    uint8_t sbeSensorOffset = 0;
+    if (!fetchSensorInfo(PLDM_OEM_IBM_SBE_HRESET_STATE, sensorToSbeInstance,
+                         sbeSensorOffset))
+    {
+        return false;
+    }
+
+    // register signal change listener
+    std::string hresetStatus = "requested";
+    constexpr auto interface = "xyz.openbmc_project.PLDM.Event";
+    constexpr auto path      = "/xyz/openbmc_project/pldm";
+    constexpr auto member    = "StateSensorEvent";
+
+    auto bus = sdbusplus::bus::new_default();
+    std::unique_ptr<sdbusplus::bus::match_t> match =
+        std::make_unique<sdbusplus::bus::match_t>(
+            bus,
+            sdbusplus::bus::match::rules::type::signal() +
+                sdbusplus::bus::match::rules::member(member) +
+                sdbusplus::bus::match::rules::path(path) +
+                sdbusplus::bus::match::rules::interface(interface),
+            [&](auto& msg) {
+                uint8_t sensorTid{};
+                uint16_t sensorId{};
+                uint8_t msgSensorOffset{};
+                uint8_t eventState{};
+                uint8_t previousEventState{};
+
+                // get sensor event details
+                msg.read(sensorTid, sensorId, msgSensorOffset, eventState,
+                         previousEventState);
+
+                // does sensor offset match?
+                if (sbeSensorOffset == msgSensorOffset)
+                {
+                    // does sensor ID match?
+                    auto sensorEntry = sensorToSbeInstance.find(sensorId);
+                    if (sensorEntry != sensorToSbeInstance.end())
+                    {
+                        const uint8_t instance = sensorEntry->second;
+
+                        // if instances matche check status
+                        if (instance == sbeInstance)
+                        {
+                            if (eventState ==
+                                static_cast<uint8_t>(SBE_HRESET_READY))
+                            {
+                                hresetStatus = "success";
+                            }
+                            else if (eventState ==
+                                     static_cast<uint8_t>(SBE_HRESET_FAILED))
+                            {
+                                hresetStatus = "fail";
+                            }
+                        }
+                    }
+                }
+            });
+
+    // send request to issue hreset of sbe
+    int pldmFd = -1; // mctp socket file descriptor
+    if (!sendPldm(request, hbrtMctpEid, pldmFd))
+    {
+        trace::err("send pldm request failed");
+        if (-1 != pldmFd)
+        {
+            close(pldmFd);
+        }
+        return false;
+    }
+
+    // keep track of elapsed time
+    uint64_t timeRemaining = 60000000; // microseconds, 1 minute
+    std::chrono::steady_clock::time_point begin =
+        std::chrono::steady_clock::now();
+
+    // wait for status update or timeout
+    trace::inf("waiting on sbe hreset");
+    while ("requested" == hresetStatus && 0 != timeRemaining)
+    {
+        bus.wait(timeRemaining);
+        uint64_t timeElapsed =
+            std::chrono::duration_cast<std::chrono::microseconds>(
+                std::chrono::steady_clock::now() - begin)
+                .count();
+
+        timeRemaining =
+            timeElapsed > timeRemaining ? 0 : timeRemaining - timeElapsed;
+
+        bus.process_discard();
+    }
+
+    if (0 == timeRemaining)
+    {
+        trace::err("hreset timed out");
+    }
+
+    close(pldmFd); // close pldm socket
+
+    return hresetStatus == "success" ? true : false;
+}
+
+} // namespace pldm
+} // namespace util
diff --git a/util/pldm.hpp b/util/pldm.hpp
new file mode 100644
index 0000000..c5d4057
--- /dev/null
+++ b/util/pldm.hpp
@@ -0,0 +1,20 @@
+#pragma once
+
+namespace util
+{
+namespace pldm
+{
+/*
+ *  @brief HRESET the SBE
+ *
+ *  @pre Host must be running
+ *
+ *  @param[in] sbeInstance - SBE to target (0 based)
+ *
+ *  @return true if HRESET successful
+ *
+ */
+bool hresetSbe(unsigned int sbeInstance);
+
+} // namespace pldm
+} // namespace util
