Fix unsanitized value updated on inherited FRUs

This commit fixes unsanitized user input values getting updated on
inherited FRUs and common interfaces via Manager updateKeyword API.
The keyword value on inherited FRUs and on common interfaces should be
updated with same value as written on hardware and base FRU.

Change-Id: I4bdb650deed685174b55c91349beec5d9643fe3e
Signed-off-by: Souvik Roy <souvikroyofficial10@gmail.com>
diff --git a/vpd-manager/include/parser.hpp b/vpd-manager/include/parser.hpp
index 9af3088..2e32ca5 100644
--- a/vpd-manager/include/parser.hpp
+++ b/vpd-manager/include/parser.hpp
@@ -70,6 +70,29 @@
     int updateVpdKeyword(const types::WriteVpdParams& i_paramsToWriteData);
 
     /**
+     * @brief Update keyword value.
+     *
+     * This API is used to update keyword value on the EEPROM path and its
+     * redundant path(s) if any taken from system config JSON. And also updates
+     * keyword value on DBus.
+     *
+     * To update IPZ type VPD, input parameter for writing should be in the form
+     * of (Record, Keyword, Value). Eg: ("VINI", "SN", {0x01, 0x02, 0x03}).
+     *
+     * To update Keyword type VPD, input parameter for writing should be in the
+     * form of (Keyword, Value). Eg: ("PE", {0x01, 0x02, 0x03}).
+     *
+     * @param[in] i_paramsToWriteData - Input details.
+     * @param[in] o_updatedValue - Actual value which has been updated on
+     * hardware.
+     *
+     * @return On success returns number of bytes written, on failure returns
+     * -1.
+     */
+    int updateVpdKeyword(const types::WriteVpdParams& i_paramsToWriteData,
+                         types::DbusVariantType& o_updatedValue);
+
+    /**
      * @brief Update keyword value on hardware.
      *
      * This API is used to update keyword value on the hardware path.
diff --git a/vpd-manager/src/manager.cpp b/vpd-manager/src/manager.cpp
index e706077..a4be32c 100644
--- a/vpd-manager/src/manager.cpp
+++ b/vpd-manager/src/manager.cpp
@@ -193,7 +193,10 @@
     {
         std::shared_ptr<Parser> l_parserObj =
             std::make_shared<Parser>(l_fruPath, l_sysCfgJsonObj);
-        auto l_rc = l_parserObj->updateVpdKeyword(i_paramsToWriteData);
+
+        types::DbusVariantType l_updatedValue;
+        auto l_rc =
+            l_parserObj->updateVpdKeyword(i_paramsToWriteData, l_updatedValue);
 
         if (l_rc != constants::FAILURE && m_backupAndRestoreObj)
         {
@@ -206,18 +209,54 @@
             }
         }
 
+        types::WriteVpdParams l_writeParams;
+        types::BinaryVector l_valueToUpdate;
+
+        if (const types::IpzData* l_ipzData =
+                std::get_if<types::IpzData>(&i_paramsToWriteData))
+        {
+            if (const types::BinaryVector* l_val =
+                    std::get_if<types::BinaryVector>(&l_updatedValue))
+            {
+                l_valueToUpdate = *l_val;
+            }
+            else
+            {
+                l_valueToUpdate = std::get<2>(*l_ipzData);
+            }
+            l_writeParams =
+                std::make_tuple(std::get<0>(*l_ipzData),
+                                std::get<1>(*l_ipzData), l_valueToUpdate);
+        }
+        else if (const types::KwData* l_kwData =
+                     std::get_if<types::KwData>(&i_paramsToWriteData))
+        {
+            if (const types::BinaryVector* l_val =
+                    std::get_if<types::BinaryVector>(&l_updatedValue))
+            {
+                l_valueToUpdate = *l_val;
+            }
+            else
+            {
+                l_valueToUpdate = std::get<1>(*l_kwData);
+            }
+
+            l_writeParams =
+                std::make_tuple(std::get<0>(*l_kwData), l_valueToUpdate);
+        }
+
         // update keyword in inherited FRUs
         if (l_rc != constants::FAILURE)
         {
             vpdSpecificUtility::updateKwdOnInheritedFrus(
-                l_fruPath, i_paramsToWriteData, l_sysCfgJsonObj);
+                l_fruPath, l_writeParams, l_sysCfgJsonObj);
         }
 
         // update common interface(s) properties
         if (l_rc != constants::FAILURE)
         {
             vpdSpecificUtility::updateCiPropertyOfInheritedFrus(
-                l_fruPath, i_paramsToWriteData, l_sysCfgJsonObj);
+                l_fruPath, l_writeParams, l_sysCfgJsonObj);
         }
 
         return l_rc;
diff --git a/vpd-manager/src/parser.cpp b/vpd-manager/src/parser.cpp
index cede920..7658011 100644
--- a/vpd-manager/src/parser.cpp
+++ b/vpd-manager/src/parser.cpp
@@ -57,7 +57,8 @@
     return l_parser->parse();
 }
 
-int Parser::updateVpdKeyword(const types::WriteVpdParams& i_paramsToWriteData)
+int Parser::updateVpdKeyword(const types::WriteVpdParams& i_paramsToWriteData,
+                             types::DbusVariantType& o_updatedValue)
 {
     int l_bytesUpdatedOnHardware = constants::FAILURE;
 
@@ -146,6 +147,9 @@
                         l_vpdParserInstance->readKeywordFromHardware(
                             types::ReadVpdParams(
                                 std::make_tuple(l_recordName, l_propertyName)));
+
+                    // return the actual value updated on hardware
+                    o_updatedValue = l_keywordValue;
                 }
                 catch (const std::exception& l_exception)
                 {
@@ -231,6 +235,12 @@
     return l_bytesUpdatedOnHardware;
 }
 
+int Parser::updateVpdKeyword(const types::WriteVpdParams& i_paramsToWriteData)
+{
+    types::DbusVariantType o_updatedValue;
+    return updateVpdKeyword(i_paramsToWriteData, o_updatedValue);
+}
+
 int Parser::updateVpdKeywordOnRedundantPath(
     const std::string& i_fruPath,
     const types::WriteVpdParams& i_paramsToWriteData)