Adding support for GetDatetime BIOS command in pldmtool.

./pldmtool -h
PLDM requester tool for OpenBMC
Usage: ./pldmtool [OPTIONS] SUBCOMMAND

Options:
  -h,--help                   Print this help message and exit

Subcommands:
  raw                         send a raw request and print response
  base                        base type command
  bios                        bios type command

./pldmtool bios -h
bios type command
Usage: ./pldmtool bios [OPTIONS] SUBCOMMAND

Options:
  -h,--help                   Print this help message and exit

Subcommands:
  GetDateTime                 get date time

./pldmtool bios GetDateTime
Encode request successfully
Request Message:
08 01 80 03 0c
Success in creating the socket : RC = 3
Success in connecting to socket : RC = 0
Success in sending message type as pldm to mctp : RC = 0
Write to socket successful : RC = 5
Total length:5
Loopback response message:
08 01 80 03 0c
On first recv(),response == request : RC = 0
Total length: 13
Shutdown Socket successful :  RC = 0
Response Message:
08 01 00 03 0c 00 01 05 12 11 12 19 20
Date & Time :
DD-MM-YYYY HH:MM:SS - 11-12-2019 12:05:01

Signed-off-by: Sridevi Ramesh <sridevra@in.ibm.com>
Change-Id: If12ddc7da19ae2c810b6c8cd99177efa1b6113ad
diff --git a/tool/meson.build b/tool/meson.build
index 8d83bda..1c55710 100644
--- a/tool/meson.build
+++ b/tool/meson.build
@@ -1,6 +1,7 @@
 sources = [
   'pldm_cmd_helper.cpp',
   'pldm_base_cmd.cpp',
+  'pldm_bios_cmd.cpp',
   'pldmtool.cpp'
 ]
 
diff --git a/tool/pldm_bios_cmd.cpp b/tool/pldm_bios_cmd.cpp
new file mode 100644
index 0000000..547955e
--- /dev/null
+++ b/tool/pldm_bios_cmd.cpp
@@ -0,0 +1,97 @@
+#include "pldm_bios_cmd.hpp"
+
+#include "pldm_cmd_helper.hpp"
+
+#include <map>
+#include <memory>
+#include <string>
+#include <typeinfo>
+#include <vector>
+
+#include "libpldm/utils.h"
+
+namespace pldmtool
+{
+
+namespace bios
+{
+
+namespace
+{
+
+using namespace pldmtool::helper;
+
+std::vector<std::unique_ptr<CommandInterface>> commands;
+
+} // namespace
+
+class GetDateTime : public CommandInterface
+{
+  public:
+    ~GetDateTime() = default;
+    GetDateTime() = delete;
+    GetDateTime(const GetDateTime&) = delete;
+    GetDateTime(GetDateTime&&) = default;
+    GetDateTime& operator=(const GetDateTime&) = delete;
+    GetDateTime& operator=(GetDateTime&&) = default;
+
+    using CommandInterface::CommandInterface;
+
+    std::pair<int, std::vector<uint8_t>> createRequestMsg() override
+    {
+        std::vector<uint8_t> requestMsg(sizeof(pldm_msg_hdr));
+        auto request = reinterpret_cast<pldm_msg*>(requestMsg.data());
+
+        auto rc = encode_get_date_time_req(PLDM_LOCAL_INSTANCE_ID, request);
+        return {rc, requestMsg};
+    }
+
+    void parseResponseMsg(pldm_msg* responsePtr, size_t payloadLength) override
+    {
+        uint8_t cc = 0;
+
+        uint8_t seconds, minutes, hours, day, month;
+        uint16_t year;
+        auto rc =
+            decode_get_date_time_resp(responsePtr, payloadLength, &cc, &seconds,
+                                      &minutes, &hours, &day, &month, &year);
+        if (rc != PLDM_SUCCESS || cc != PLDM_SUCCESS)
+        {
+            std::cerr << "Response Message Error: "
+                      << "rc=" << rc << ",cc=" << (int)cc << std::endl;
+            return;
+        }
+        std::cout << "Date & Time : " << std::endl;
+        std::cout << "DD-MM-YYYY HH:MM:SS - ";
+        setWidth(day);
+        std::cout << "-";
+        setWidth(month);
+        std::cout << "-" << bcd2dec16(year) << " ";
+        setWidth(hours);
+        std::cout << ":";
+        setWidth(minutes);
+        std::cout << ":";
+        setWidth(seconds);
+        std::cout << std::endl;
+    }
+
+  private:
+    void setWidth(uint8_t data)
+    {
+        std::cout << std::setfill('0') << std::setw(2)
+                  << static_cast<uint32_t>(bcd2dec8(data));
+    }
+};
+
+void registerCommand(CLI::App& app)
+{
+    auto bios = app.add_subcommand("bios", "bios type command");
+    bios->require_subcommand(1);
+    auto getDateTime = bios->add_subcommand("GetDateTime", "get date time");
+    commands.push_back(
+        std::make_unique<GetDateTime>("bios", "GetDateTime", getDateTime));
+}
+
+} // namespace bios
+
+} // namespace pldmtool
diff --git a/tool/pldm_bios_cmd.hpp b/tool/pldm_bios_cmd.hpp
new file mode 100644
index 0000000..4448f7e
--- /dev/null
+++ b/tool/pldm_bios_cmd.hpp
@@ -0,0 +1,14 @@
+#pragma once
+
+#include <CLI/CLI.hpp>
+
+namespace pldmtool
+{
+
+namespace bios
+{
+
+void registerCommand(CLI::App& app);
+}
+
+} // namespace pldmtool
diff --git a/tool/pldm_cmd_helper.hpp b/tool/pldm_cmd_helper.hpp
index a162de4..fbc87d7 100644
--- a/tool/pldm_cmd_helper.hpp
+++ b/tool/pldm_cmd_helper.hpp
@@ -14,6 +14,7 @@
 #include <utility>
 
 #include "libpldm/base.h"
+#include "libpldm/bios.h"
 #include "libpldm/platform.h"
 
 namespace pldmtool
diff --git a/tool/pldmtool.cpp b/tool/pldmtool.cpp
index 7244e47..059bd8e 100644
--- a/tool/pldmtool.cpp
+++ b/tool/pldmtool.cpp
@@ -1,4 +1,5 @@
 #include "pldm_base_cmd.hpp"
+#include "pldm_bios_cmd.hpp"
 #include "pldm_cmd_helper.hpp"
 
 #include <CLI/CLI.hpp>
@@ -66,6 +67,7 @@
 
     pldmtool::raw::registerCommand(app);
     pldmtool::base::registerCommand(app);
+    pldmtool::bios::registerCommand(app);
 
     CLI11_PARSE(app, argc, argv);
     return 0;