diff --git a/requester/README.md b/requester/README.md
new file mode 100644
index 0000000..fd5ebd1
--- /dev/null
+++ b/requester/README.md
@@ -0,0 +1,43 @@
+## Overview
+
+PLDM requester infrastructure enables the requester code in PLDM daemon to
+meet the requirements of PLDM requesters. It provides the following features:
+
+- Register a PLDM request and the response handler to be invoked on receiving
+  the response.
+- The handling of the request and response is asynchronous. This means the PLDM
+  daemon is not blocked till the response is received for a request.
+- Multiple outstanding requests are supported.
+- Request retries based on the time-out waiting for a response.
+- Instance ID expiration and marking the instance ID free after expiration.
+
+Future enhancements:
+
+- A mechanism to queue multiple outstanding requests to the same responder.
+- Handle ERROR_NOT_READY completion code and retry the PLDM request after 250ms
+  interval.
+
+The requester code needs to use the `registerRequest` API to register the PLDM
+request. The destination endpoint ID, instance ID, PLDM type, PLDM command code,
+PLDM request message (PLDM header and payload) and response function handler are
+passed as parameters to the registerRequest API.
+
+```
+    int registerRequest(mctp_eid_t eid, uint8_t instanceId, uint8_t type,
+                        uint8_t command, pldm::Request&& requestMsg,
+                        ResponseHandler&& responseHandler)
+```
+
+The signature of the response function handler:
+```
+void handler(mctp_eid_t eid, const pldm_msg* response, size_t respMsgLen)
+```
+
+- If the response is received before instance ID expiration:
+  - If the response matches with an outstanding request then the response
+    handler is invoked.
+  - If the response does not match with the PLDM instance ID, PLDM type and PLDM
+    command code of an outstanding request, then no action is taken on the
+    response.
+- Once the instance ID is expired, then the response handler is invoked with
+  empty response, so that further action can be taken.
diff --git a/requester/handler.hpp b/requester/handler.hpp
new file mode 100644
index 0000000..2082f69
--- /dev/null
+++ b/requester/handler.hpp
@@ -0,0 +1,279 @@
+#pragma once
+
+#include "config.h"
+
+#include "libpldm/base.h"
+#include "libpldm/requester/pldm.h"
+
+#include "common/types.hpp"
+#include "pldmd/dbus_impl_requester.hpp"
+#include "request.hpp"
+
+#include <function2/function2.hpp>
+#include <sdbusplus/timer.hpp>
+#include <sdeventplus/event.hpp>
+#include <sdeventplus/source/event.hpp>
+
+#include <cassert>
+#include <chrono>
+#include <memory>
+#include <tuple>
+#include <unordered_map>
+
+namespace pldm
+{
+
+namespace requester
+{
+
+/** @struct RequestKey
+ *
+ *  RequestKey uniquely identifies the PLDM request message to match it with the
+ *  response and a combination of MCTP endpoint ID, PLDM instance ID, PLDM type
+ *  and PLDM command is the key.
+ */
+struct RequestKey
+{
+    mctp_eid_t eid;     //!< MCTP endpoint ID
+    uint8_t instanceId; //!< PLDM instance ID
+    uint8_t type;       //!< PLDM type
+    uint8_t command;    //!< PLDM command
+
+    bool operator==(const RequestKey& e) const
+    {
+        return ((eid == e.eid) && (instanceId == e.instanceId) &&
+                (type == e.type) && (command == e.command));
+    }
+};
+
+/** @struct RequestKeyHasher
+ *
+ *  This is a simple hash function, since the instance ID generator API
+ *  generates unique instance IDs for MCTP endpoint ID.
+ */
+struct RequestKeyHasher
+{
+    std::size_t operator()(const RequestKey& key) const
+    {
+        return (key.eid << 24 | key.instanceId << 16 | key.type << 8 |
+                key.command);
+    }
+};
+
+using ResponseHandler = fu2::unique_function<void(
+    mctp_eid_t eid, const pldm_msg* response, size_t respMsgLen)>;
+using namespace std::chrono;
+using namespace sdeventplus;
+using namespace sdeventplus::source;
+using namespace pldm::dbus_api;
+using namespace phosphor;
+
+/** @class Handler
+ *
+ *  This class handles the lifecycle of the PLDM request message based on the
+ *  instance ID expiration interval, number of request retries and the timeout
+ *  waiting for a response. The registered response handlers are invoked with
+ *  response once the PLDM responder sends the response. If no response is
+ *  received within the instance ID expiration interval or any other failure the
+ *  response handler is invoked with the empty response.
+ *
+ * @tparam RequestInterface - Request class type
+ */
+template <class RequestInterface>
+class Handler
+{
+
+  public:
+    Handler() = delete;
+    Handler(const Handler&) = delete;
+    Handler(Handler&&) = delete;
+    Handler& operator=(const Handler&) = delete;
+    Handler& operator=(Handler&&) = delete;
+    ~Handler() = default;
+
+    /** @brief Constructor
+     *
+     *  @param[in] fd - fd of MCTP communications socket
+     *  @param[in] event - reference to PLDM daemon's main event loop
+     *  @param[in] requester - reference to Requester object
+     *  @param[in] instanceIdExpiryInterval - instance ID expiration interval
+     *  @param[in] numRetries - number of request retries
+     *  @param[in] responseTimeOut - time to wait between each retry
+     */
+    explicit Handler(
+        int fd, Event& event, Requester& requester,
+        seconds instanceIdExpiryInterval =
+            seconds(INSTANCE_ID_EXPIRATION_INTERVAL),
+        uint8_t numRetries = static_cast<uint8_t>(NUMBER_OF_REQUEST_RETRIES),
+        milliseconds responseTimeOut = milliseconds(RESPONSE_TIME_OUT)) :
+        fd(fd),
+        event(event), requester(requester),
+        instanceIdExpiryInterval(instanceIdExpiryInterval),
+        numRetries(numRetries), responseTimeOut(responseTimeOut)
+    {}
+
+    /** @brief Register a PLDM request message
+     *
+     *  @param[in] eid - endpoint ID of the remote MCTP endpoint
+     *  @param[in] instanceId - instance ID to match request and response
+     *  @param[in] type - PLDM type
+     *  @param[in] command - PLDM command
+     *  @param[in] requestMsg - PLDM request message
+     *  @param[in] responseHandler - Response handler for this request
+     *
+     *  @return return PLDM_SUCCESS on success and PLDM_ERROR otherwise
+     */
+    int registerRequest(mctp_eid_t eid, uint8_t instanceId, uint8_t type,
+                        uint8_t command, pldm::Request&& requestMsg,
+                        ResponseHandler&& responseHandler)
+    {
+        RequestKey key{eid, instanceId, type, command};
+
+        auto instanceIdExpiryCallBack = [key, this](void) {
+            if (this->handlers.contains(key))
+            {
+                std::cerr << "Response not received for the request, instance "
+                             "ID expired."
+                          << " EID = " << key.eid
+                          << " INSTANCE_ID = " << key.instanceId
+                          << " TYPE = " << key.type
+                          << " COMMAND = " << key.command << "\n";
+                auto& [request, responseHandler, timerInstance] =
+                    this->handlers[key];
+                request->stop();
+                auto rc = timerInstance->stop();
+                if (rc)
+                {
+                    std::cerr
+                        << "Failed to stop the instance ID expiry timer. RC = "
+                        << rc << "\n";
+                }
+                // Call response handler with an empty response to indicate no
+                // response
+                responseHandler(key.eid, nullptr, 0);
+                this->removeRequestContainer.emplace(
+                    key, std::make_unique<sdeventplus::source::Defer>(
+                             event, std::bind(&Handler::removeRequestEntry,
+                                              this, key)));
+            }
+            else
+            {
+                // This condition is not possible, if a response is received
+                // before the instance ID expiry, then the response handler
+                // is executed and the entry will be removed.
+                assert(false);
+            }
+        };
+
+        auto request = std::make_unique<RequestInterface>(
+            fd, eid, event, std::move(requestMsg), numRetries, responseTimeOut);
+        auto timer = std::make_unique<phosphor::Timer>(
+            event.get(), instanceIdExpiryCallBack);
+
+        auto rc = request->start();
+        if (rc != PLDM_SUCCESS)
+        {
+            std::cerr << "Failure to send the PLDM request message"
+                      << "\n";
+            return rc;
+        }
+
+        try
+        {
+            timer->start(duration_cast<microseconds>(instanceIdExpiryInterval));
+        }
+        catch (const std::runtime_error& e)
+        {
+            std::cerr << "Failed to start the instance ID expiry timer. RC = "
+                      << e.what() << "\n";
+            return PLDM_ERROR;
+        }
+
+        handlers.emplace(key, std::make_tuple(std::move(request),
+                                              std::move(responseHandler),
+                                              std::move(timer)));
+        return rc;
+    }
+
+    /** @brief Handle PLDM response message
+     *
+     *  @param[in] eid - endpoint ID of the remote MCTP endpoint
+     *  @param[in] instanceId - instance ID to match request and response
+     *  @param[in] type - PLDM type
+     *  @param[in] command - PLDM command
+     *  @param[in] response - PLDM response message
+     *  @param[in] respMsgLen - length of the response message
+     */
+    void handleResponse(mctp_eid_t eid, uint8_t instanceId, uint8_t type,
+                        uint8_t command, const pldm_msg* response,
+                        size_t respMsgLen)
+    {
+        RequestKey key{eid, instanceId, type, command};
+        if (handlers.contains(key))
+        {
+            auto& [request, responseHandler, timerInstance] = handlers[key];
+            request->stop();
+            auto rc = timerInstance->stop();
+            if (rc)
+            {
+                std::cerr
+                    << "Failed to stop the instance ID expiry timer. RC = "
+                    << rc << "\n";
+            }
+            responseHandler(eid, response, respMsgLen);
+            requester.markFree(key.eid, key.instanceId);
+            handlers.erase(key);
+        }
+        else
+        {
+            // Got a response for a PLDM request message not registered with the
+            // request handler, so freeing up the instance ID, this can be other
+            // OpenBMC applications relying on PLDM D-Bus apis like
+            // openpower-occ-control and softoff
+            requester.markFree(key.eid, key.instanceId);
+        }
+    }
+
+  private:
+    int fd;               //!< file descriptor of MCTP communications socket
+    Event& event;         //!< reference to PLDM daemon's main event loop
+    Requester& requester; //!< reference to Requester object
+    seconds instanceIdExpiryInterval; //!< Instance ID expiration interval
+    uint8_t numRetries;               //!< number of request retries
+    milliseconds responseTimeOut;     //!< time to wait between each retry
+
+    /** @brief Container for storing the details of the PLDM request message,
+     *         handler for the corresponding PLDM response and the timer object
+     *         for the Instance ID expiration
+     */
+    using RequestValue = std::tuple<std::unique_ptr<RequestInterface>,
+                                    ResponseHandler, std::unique_ptr<Timer>>;
+
+    /** @brief Container for storing the PLDM request entries */
+    std::unordered_map<RequestKey, RequestValue, RequestKeyHasher> handlers;
+
+    /** @brief Container to store information about the request entries to be
+     *         removed after the instance ID timer expires
+     */
+    std::unordered_map<RequestKey, std::unique_ptr<Defer>, RequestKeyHasher>
+        removeRequestContainer;
+
+    /** @brief Remove request entry for which the instance ID expired
+     *
+     *  @param[in] key - key for the Request
+     */
+    void removeRequestEntry(RequestKey key)
+    {
+        if (removeRequestContainer.contains(key))
+        {
+            removeRequestContainer[key].reset();
+            requester.markFree(key.eid, key.instanceId);
+            handlers.erase(key);
+            removeRequestContainer.erase(key);
+        }
+    }
+};
+
+} // namespace requester
+
+} // namespace pldm
diff --git a/requester/request.hpp b/requester/request.hpp
new file mode 100644
index 0000000..4097e10
--- /dev/null
+++ b/requester/request.hpp
@@ -0,0 +1,179 @@
+#pragma once
+
+#include "libpldm/base.h"
+#include "libpldm/requester/pldm.h"
+
+#include "common/types.hpp"
+
+#include <sdbusplus/timer.hpp>
+#include <sdeventplus/event.hpp>
+
+#include <chrono>
+#include <functional>
+#include <iostream>
+
+namespace pldm
+{
+
+namespace requester
+{
+
+using namespace std::chrono;
+
+/** @class RequestRetryTimer
+ *
+ *  The abstract base class for implementing the PLDM request retry logic. This
+ *  class handles number of times the PLDM request needs to be retried if the
+ *  response is not received and the time to wait between each retry. It
+ *  provides APIs to start and stop the request flow.
+ */
+class RequestRetryTimer
+{
+  public:
+    RequestRetryTimer() = delete;
+    RequestRetryTimer(const RequestRetryTimer&) = delete;
+    RequestRetryTimer(RequestRetryTimer&&) = default;
+    RequestRetryTimer& operator=(const RequestRetryTimer&) = delete;
+    RequestRetryTimer& operator=(RequestRetryTimer&&) = default;
+    virtual ~RequestRetryTimer() = default;
+
+    /** @brief Constructor
+     *
+     *  @param[in] event - reference to PLDM daemon's main event loop
+     *  @param[in] numRetries - number of request retries
+     *  @param[in] timeout - time to wait between each retry in milliseconds
+     */
+    explicit RequestRetryTimer(sdeventplus::Event& event, uint8_t numRetries,
+                               milliseconds timeout) :
+
+        event(event),
+        numRetries(numRetries), timeout(timeout),
+        timer(event.get(), std::bind_front(&RequestRetryTimer::callback, this))
+    {}
+
+    /** @brief Starts the request flow and arms the timer for request retries
+     *
+     *  @return return PLDM_SUCCESS on success and PLDM_ERROR otherwise
+     */
+    int start()
+    {
+        auto rc = send();
+        if (rc != PLDM_SUCCESS)
+        {
+            return rc;
+        }
+
+        try
+        {
+            if (numRetries)
+            {
+                timer.start(duration_cast<microseconds>(timeout), true);
+            }
+        }
+        catch (const std::runtime_error& e)
+        {
+            std::cerr << "Failed to start the request timer. RC = " << e.what()
+                      << "\n";
+            return PLDM_ERROR;
+        }
+
+        return PLDM_SUCCESS;
+    }
+
+    /** @brief Stops the timer and no further request retries happen */
+    void stop()
+    {
+        auto rc = timer.stop();
+        if (rc)
+        {
+            std::cerr << "Failed to stop the request timer. RC = " << rc
+                      << "\n";
+        }
+    }
+
+  protected:
+    sdeventplus::Event& event; //!< reference to PLDM daemon's main event loop
+    uint8_t numRetries;        //!< number of request retries
+    milliseconds timeout;  //!< time to wait between each retry in milliseconds
+    phosphor::Timer timer; //!< manages starting timers and handling timeouts
+
+    /** @brief Sends the PLDM request message
+     *
+     *  @return return PLDM_SUCCESS on success and PLDM_ERROR otherwise
+     */
+    virtual int send() const = 0;
+
+    /** @brief Callback function invoked when the timeout happens */
+    void callback()
+    {
+        if (numRetries--)
+        {
+            send();
+        }
+        else
+        {
+            stop();
+        }
+    }
+};
+
+/** @class Request
+ *
+ *  The concrete implementation of RequestIntf. This class implements the send()
+ *  to send the PLDM request message over MCTP socket.
+ *  This class encapsulates the PLDM request message, the number of times the
+ *  request needs to retried if the response is not received and the amount of
+ *  time to wait between each retry. It provides APIs to start and stop the
+ *  request flow.
+ */
+class Request final : public RequestRetryTimer
+{
+  public:
+    Request() = delete;
+    Request(const Request&) = delete;
+    Request(Request&&) = default;
+    Request& operator=(const Request&) = delete;
+    Request& operator=(Request&&) = default;
+    ~Request() = default;
+
+    /** @brief Constructor
+     *
+     *  @param[in] fd - fd of the MCTP communication socket
+     *  @param[in] eid - endpoint ID of the remote MCTP endpoint
+     *  @param[in] event - reference to PLDM daemon's main event loop
+     *  @param[in] requestMsg - PLDM request message
+     *  @param[in] numRetries - number of request retries
+     *  @param[in] timeout - time to wait between each retry in milliseconds
+     */
+    explicit Request(int fd, mctp_eid_t eid, sdeventplus::Event& event,
+                     pldm::Request&& requestMsg, uint8_t numRetries,
+                     milliseconds timeout) :
+        RequestRetryTimer(event, numRetries, timeout),
+        fd(fd), eid(eid), requestMsg(std::move(requestMsg))
+    {}
+
+  private:
+    int fd;         //!< file descriptor of MCTP communications socket
+    mctp_eid_t eid; //!< endpoint ID of the remote MCTP endpoint
+    pldm::Request&& requestMsg; //!< PLDM request message
+
+    /** @brief Sends the PLDM request message on the socket
+     *
+     *  @return return PLDM_SUCCESS on success and PLDM_ERROR otherwise
+     */
+    int send() const
+    {
+        auto rc = pldm_send(eid, fd, requestMsg.data(), requestMsg.size());
+        if (rc < 0)
+        {
+            std::cerr << "Failed to send PLDM message. RC = " << rc
+                      << ", errno = " << errno << "\n";
+            return PLDM_ERROR;
+        }
+        return PLDM_SUCCESS;
+    }
+};
+
+} // namespace requester
+
+} // namespace pldm
\ No newline at end of file
diff --git a/requester/test/handler_test.cpp b/requester/test/handler_test.cpp
new file mode 100644
index 0000000..7230b08
--- /dev/null
+++ b/requester/test/handler_test.cpp
@@ -0,0 +1,149 @@
+#include "libpldm/base.h"
+
+#include "common/types.hpp"
+#include "common/utils.hpp"
+#include "mock_request.hpp"
+#include "pldmd/dbus_impl_requester.hpp"
+#include "requester/handler.hpp"
+
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+
+using namespace pldm::requester;
+using namespace std::chrono;
+
+using ::testing::AtLeast;
+using ::testing::Between;
+using ::testing::Exactly;
+using ::testing::NiceMock;
+using ::testing::Return;
+
+class HandlerTest : public testing::Test
+{
+  protected:
+    HandlerTest() :
+        event(sdeventplus::Event::get_default()),
+        dbusImplReq(pldm::utils::DBusHandler::getBus(),
+                    "/xyz/openbmc_project/pldm")
+    {}
+
+    int fd = 0;
+    mctp_eid_t eid = 0;
+    sdeventplus::Event event;
+    pldm::dbus_api::Requester dbusImplReq;
+
+    /** @brief This function runs the sd_event_run in a loop till all the events
+     *         in the testcase are dispatched and exits when there are no events
+     *         for the timeout time.
+     *
+     *  @param[in] timeout - maximum time to wait for an event
+     */
+    void waitEventExpiry(milliseconds timeout)
+    {
+        while (1)
+        {
+            auto sleepTime = duration_cast<microseconds>(timeout);
+            // Returns 0 on timeout
+            if (!sd_event_run(event.get(), sleepTime.count()))
+            {
+                break;
+            }
+        }
+    }
+
+  public:
+    bool nullResponse = false;
+    bool validResponse = false;
+    int callbackCount = 0;
+    bool response2 = false;
+
+    void pldmResponseCallBack(mctp_eid_t /*eid*/, const pldm_msg* response,
+                              size_t respMsgLen)
+    {
+        if (response == nullptr && respMsgLen == 0)
+        {
+            nullResponse = true;
+        }
+        else
+        {
+            validResponse = true;
+        }
+        callbackCount++;
+    }
+};
+
+TEST_F(HandlerTest, singleRequestResponseScenario)
+{
+    Handler<NiceMock<MockRequest>> reqHandler(fd, event, dbusImplReq,
+                                              seconds(1), 2, milliseconds(100));
+    pldm::Request request{};
+    auto instanceId = dbusImplReq.getInstanceId(eid);
+    reqHandler.registerRequest(
+        eid, instanceId, 0, 0, std::move(request),
+        std::move(std::bind_front(&HandlerTest::pldmResponseCallBack, this)));
+
+    pldm::Response response(sizeof(pldm_msg_hdr) + sizeof(uint8_t));
+    auto responsePtr = reinterpret_cast<const pldm_msg*>(response.data());
+    reqHandler.handleResponse(eid, instanceId, 0, 0, responsePtr,
+                              sizeof(response));
+
+    // handleResponse() will free the instance ID after calling the response
+    // handler, so the same instance ID is granted next as well
+    ASSERT_EQ(validResponse, true);
+    ASSERT_EQ(instanceId, dbusImplReq.getInstanceId(eid));
+}
+
+TEST_F(HandlerTest, singleRequestInstanceIdTimerExpired)
+{
+    Handler<NiceMock<MockRequest>> reqHandler(fd, event, dbusImplReq,
+                                              seconds(1), 2, milliseconds(100));
+    pldm::Request request{};
+    auto instanceId = dbusImplReq.getInstanceId(eid);
+    reqHandler.registerRequest(
+        eid, instanceId, 0, 0, std::move(request),
+        std::move(std::bind_front(&HandlerTest::pldmResponseCallBack, this)));
+
+    // Waiting for 500ms so that the instance ID expiry callback is invoked
+    waitEventExpiry(milliseconds(500));
+
+    // cleanup() will free the instance ID after calling the response
+    // handler will no response, so the same instance ID is granted next
+    ASSERT_EQ(instanceId, dbusImplReq.getInstanceId(eid));
+    ASSERT_EQ(nullResponse, true);
+}
+
+TEST_F(HandlerTest, multipleRequestResponseScenario)
+{
+    Handler<NiceMock<MockRequest>> reqHandler(fd, event, dbusImplReq,
+                                              seconds(2), 2, milliseconds(100));
+    pldm::Request request{};
+    auto instanceId = dbusImplReq.getInstanceId(eid);
+    reqHandler.registerRequest(
+        eid, instanceId, 0, 0, std::move(request),
+        std::move(std::bind_front(&HandlerTest::pldmResponseCallBack, this)));
+
+    pldm::Request requestNxt{};
+    auto instanceIdNxt = dbusImplReq.getInstanceId(eid);
+    reqHandler.registerRequest(
+        eid, instanceIdNxt, 0, 0, std::move(requestNxt),
+        std::move(std::bind_front(&HandlerTest::pldmResponseCallBack, this)));
+
+    pldm::Response response(sizeof(pldm_msg_hdr) + sizeof(uint8_t));
+    auto responsePtr = reinterpret_cast<const pldm_msg*>(response.data());
+    reqHandler.handleResponse(eid, instanceIdNxt, 0, 0, responsePtr,
+                              sizeof(response));
+    ASSERT_EQ(validResponse, true);
+    ASSERT_EQ(callbackCount, 1);
+    validResponse = false;
+
+    // Waiting for 500ms and handle the response for the first request, to
+    // simulate a delayed response for the first request
+    waitEventExpiry(milliseconds(500));
+
+    reqHandler.handleResponse(eid, instanceId, 0, 0, responsePtr,
+                              sizeof(response));
+
+    ASSERT_EQ(validResponse, true);
+    ASSERT_EQ(callbackCount, 2);
+    ASSERT_EQ(instanceId, dbusImplReq.getInstanceId(eid));
+}
\ No newline at end of file
diff --git a/requester/test/meson.build b/requester/test/meson.build
new file mode 100644
index 0000000..1f5fe17
--- /dev/null
+++ b/requester/test/meson.build
@@ -0,0 +1,25 @@
+test_src = declare_dependency(
+          sources: [
+            '../../pldmd/dbus_impl_requester.cpp',
+            '../../pldmd/instance_id.cpp'])
+
+tests = [
+  'handler_test',
+  'request_test',
+]
+
+foreach t : tests
+  test(t, executable(t.underscorify(), t + '.cpp',
+                     implicit_include_directories: false,
+                     link_args: dynamic_linker,
+                     build_rpath: get_option('oe-sdk').enabled() ? rpath : '',
+                     dependencies: [
+                         gtest,
+                         gmock,
+                         libpldm_dep,
+                         phosphor_dbus_interfaces,
+                         sdbusplus,
+                         sdeventplus,
+                         test_src]),
+       workdir: meson.current_source_dir())
+endforeach
diff --git a/requester/test/mock_request.hpp b/requester/test/mock_request.hpp
new file mode 100644
index 0000000..b8e9efb
--- /dev/null
+++ b/requester/test/mock_request.hpp
@@ -0,0 +1,30 @@
+#pragma once
+
+#include "requester/request.hpp"
+
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+
+namespace pldm
+{
+
+namespace requester
+{
+
+using namespace std::chrono;
+
+class MockRequest : public RequestRetryTimer
+{
+  public:
+    MockRequest(int /*fd*/, mctp_eid_t /*eid*/, sdeventplus::Event& event,
+                pldm::Request&& /*requestMsg*/, uint8_t numRetries,
+                milliseconds responseTimeOut) :
+        RequestRetryTimer(event, numRetries, responseTimeOut)
+    {}
+
+    MOCK_METHOD(int, send, (), (const, override));
+};
+
+} // namespace requester
+
+} // namespace pldm
\ No newline at end of file
diff --git a/requester/test/request_test.cpp b/requester/test/request_test.cpp
new file mode 100644
index 0000000..6471d9e
--- /dev/null
+++ b/requester/test/request_test.cpp
@@ -0,0 +1,101 @@
+#include "libpldm/base.h"
+
+#include "mock_request.hpp"
+
+#include <sdbusplus/timer.hpp>
+#include <sdeventplus/event.hpp>
+
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+
+using namespace pldm::requester;
+using namespace std::chrono;
+using ::testing::AtLeast;
+using ::testing::Between;
+using ::testing::Exactly;
+using ::testing::Return;
+
+class RequestIntfTest : public testing::Test
+{
+  protected:
+    RequestIntfTest() : event(sdeventplus::Event::get_default())
+    {}
+
+    /** @brief This function runs the sd_event_run in a loop till all the events
+     *         in the testcase are dispatched and exits when there are no events
+     *         for the timeout time.
+     *
+     *  @param[in] timeout - maximum time to wait for an event
+     */
+    void waitEventExpiry(milliseconds timeout)
+    {
+        while (1)
+        {
+            auto sleepTime = duration_cast<microseconds>(timeout);
+            // Returns 0 on timeout
+            if (!sd_event_run(event.get(), sleepTime.count()))
+            {
+                break;
+            }
+        }
+    }
+
+    int fd = 0;
+    mctp_eid_t eid = 0;
+    sdeventplus::Event event;
+    std::vector<uint8_t> requestMsg;
+};
+
+TEST_F(RequestIntfTest, 0Retries100msTimeout)
+{
+    MockRequest request(fd, eid, event, std::move(requestMsg), 0,
+                        milliseconds(100));
+    EXPECT_CALL(request, send())
+        .Times(Exactly(1))
+        .WillOnce(Return(PLDM_SUCCESS));
+    auto rc = request.start();
+    ASSERT_EQ(rc, PLDM_SUCCESS);
+}
+
+TEST_F(RequestIntfTest, 2Retries100msTimeout)
+{
+    MockRequest request(fd, eid, event, std::move(requestMsg), 2,
+                        milliseconds(100));
+    // send() is called a total of 3 times, the original plus two retries
+    EXPECT_CALL(request, send()).Times(3).WillRepeatedly(Return(PLDM_SUCCESS));
+    auto rc = request.start();
+    ASSERT_EQ(rc, PLDM_SUCCESS);
+    waitEventExpiry(milliseconds(500));
+}
+
+TEST_F(RequestIntfTest, 9Retries100msTimeoutRequestStoppedAfter1sec)
+{
+    MockRequest request(fd, eid, event, std::move(requestMsg), 9,
+                        milliseconds(100));
+    // send() will be called a total of 10 times, the original plus 9 retries.
+    // In a ideal scenario send() would have been called 10 times in 1 sec (when
+    // the timer is stopped) with a timeout of 100ms. Because there are delays
+    // in dispatch, the range is kept between 5 and 10. This recreates the
+    // situation where the Instance ID expires before the all the retries have
+    // been completed and the timer is stopped.
+    EXPECT_CALL(request, send())
+        .Times(Between(5, 10))
+        .WillRepeatedly(Return(PLDM_SUCCESS));
+    auto rc = request.start();
+    ASSERT_EQ(rc, PLDM_SUCCESS);
+
+    auto requestStopCallback = [&](void) { request.stop(); };
+    phosphor::Timer timer(event.get(), requestStopCallback);
+    timer.start(duration_cast<microseconds>(seconds(1)));
+
+    waitEventExpiry(milliseconds(500));
+}
+
+TEST_F(RequestIntfTest, 2Retries100msTimeoutsendReturnsError)
+{
+    MockRequest request(fd, eid, event, std::move(requestMsg), 2,
+                        milliseconds(100));
+    EXPECT_CALL(request, send()).Times(Exactly(1)).WillOnce(Return(PLDM_ERROR));
+    auto rc = request.start();
+    ASSERT_EQ(rc, PLDM_ERROR);
+}
