avoid placement new

The placement new pattern used throughout these files was flagged by
GCC-16 with -Wuninitialized and -Wmaybe-uninitialized.  Placement new
does, technically, result in an uninitialized value even though the
intent was to cast the pointer onto existing storage.  Using
`start_lifetime_as` instead better expresses the intent and avoid the
GCC-16 warnings.

GCC-15 doesn't provide `std::start_lifetime_as` yet, so provide it
in a polyfill for backwards compatibility.

There are a large number of `reinterpret_cast` calls already done in
this repository that likely should be converted to `start_lifetime_as`
to avoid undefined-behavior in later versions of GCC.

Signed-off-by: Patrick Williams <patrick@stwcx.xyz>
Change-Id: I227764f1191bbc70105200a703106c8d21e5e5eb
diff --git a/common/start_lifetime_as.hpp b/common/start_lifetime_as.hpp
new file mode 100644
index 0000000..ed6c8ee
--- /dev/null
+++ b/common/start_lifetime_as.hpp
@@ -0,0 +1,39 @@
+#pragma once
+
+#include <memory>
+
+/*
+ * C++23 [obj.lifetime] `std::start_lifetime_as` is not yet implemented in
+ * GCC-15 (no `__cpp_lib_start_lifetime_as`).  GCC-16+ may treat a bare
+ * `reinterpret_cast` as undefined behaviour because the compiler's assumed
+ * aliasing rules let it ignore that a new object now occupies the storage.
+ *
+ * The standard specifies that `start_lifetime_as` is equivalent to:
+ *   return std::launder(reinterpret_cast<T*>(p));
+ *
+ * See:
+ *   - https://wg21.link/P0593R6  (implicit object creation)
+ *   - https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2023/n4928.pdf
+ *     [obj.lifetime]
+ *
+ * This polyfill can be dropped once we move to a compiler that provides the
+ * real `std::start_lifetime_as`.
+ */
+#ifndef __cpp_lib_start_lifetime_as
+// NOLINTBEGIN(cert-dcl58-cpp)
+namespace std
+{
+template <class T>
+T* start_lifetime_as(void* p) noexcept
+{
+    return std::launder(reinterpret_cast<T*>(p));
+}
+
+template <class T>
+const T* start_lifetime_as(const void* p) noexcept
+{
+    return std::launder(reinterpret_cast<const T*>(p));
+}
+} // namespace std
+// NOLINTEND(cert-dcl58-cpp)
+#endif
diff --git a/common/utils.cpp b/common/utils.cpp
index 5ffb193..b7de564 100644
--- a/common/utils.cpp
+++ b/common/utils.cpp
@@ -1,5 +1,7 @@
 #include "utils.hpp"
 
+#include "common/start_lifetime_as.hpp"
+
 #include <libpldm/pdr.h>
 #include <libpldm/pldm_types.h>
 #include <linux/mctp.h>
@@ -17,6 +19,7 @@
 #include <fstream>
 #include <iostream>
 #include <map>
+#include <memory>
 #include <stdexcept>
 #include <string>
 #include <vector>
@@ -53,15 +56,17 @@
                                                   record, &outData, &size);
             if (record)
             {
-                auto pdr = new (outData) pldm_state_effecter_pdr;
+                auto pdr =
+                    std::start_lifetime_as<pldm_state_effecter_pdr>(outData);
                 auto compositeEffecterCount = pdr->composite_effecter_count;
                 auto possible_states_start = pdr->possible_states;
 
                 for (auto effecters = 0x00; effecters < compositeEffecterCount;
                      effecters++)
                 {
-                    auto possibleStates = new (possible_states_start)
-                        state_effecter_possible_states;
+                    auto possibleStates =
+                        std::start_lifetime_as<state_effecter_possible_states>(
+                            possible_states_start);
                     auto setId = possibleStates->state_set_id;
                     auto possibleStateSize =
                         possibleStates->possible_states_size;
@@ -104,15 +109,17 @@
                                                   record, &outData, &size);
             if (record)
             {
-                auto pdr = new (outData) pldm_state_sensor_pdr;
+                auto pdr =
+                    std::start_lifetime_as<pldm_state_sensor_pdr>(outData);
                 auto compositeSensorCount = pdr->composite_sensor_count;
                 auto possible_states_start = pdr->possible_states;
 
                 for (auto sensors = 0x00; sensors < compositeSensorCount;
                      sensors++)
                 {
-                    auto possibleStates = new (possible_states_start)
-                        state_sensor_possible_states;
+                    auto possibleStates =
+                        std::start_lifetime_as<state_sensor_possible_states>(
+                            possible_states_start);
                     auto setId = possibleStates->state_set_id;
                     auto possibleStateSize =
                         possibleStates->possible_states_size;
@@ -523,15 +530,16 @@
                                               record, &pdrData, &pdrSize);
         if (record && (localOrRemote ^ pldm_pdr_record_is_remote(record)))
         {
-            auto pdr = new (pdrData) pldm_state_effecter_pdr;
+            auto pdr = std::start_lifetime_as<pldm_state_effecter_pdr>(pdrData);
             auto compositeEffecterCount = pdr->composite_effecter_count;
             auto possible_states_start = pdr->possible_states;
 
             for (auto effecters = 0x00; effecters < compositeEffecterCount;
                  effecters++)
             {
-                auto possibleStates = new (possible_states_start)
-                    state_effecter_possible_states;
+                auto possibleStates =
+                    std::start_lifetime_as<state_effecter_possible_states>(
+                        possible_states_start);
                 auto setId = possibleStates->state_set_id;
                 auto possibleStateSize = possibleStates->possible_states_size;
 
@@ -601,14 +609,16 @@
     auto pdrs = findStateSensorPDR(tid, entityType, stateSetId, pdrRepo);
     for (auto pdr : pdrs)
     {
-        auto sensorPdr = new (pdr.data()) pldm_state_sensor_pdr;
+        auto sensorPdr =
+            std::start_lifetime_as<pldm_state_sensor_pdr>(pdr.data());
         auto compositeSensorCount = sensorPdr->composite_sensor_count;
         auto possible_states_start = sensorPdr->possible_states;
 
         for (auto sensors = 0x00; sensors < compositeSensorCount; sensors++)
         {
-            auto possibleStates = new (possible_states_start)
-                state_sensor_possible_states;
+            auto possibleStates =
+                std::start_lifetime_as<state_sensor_possible_states>(
+                    possible_states_start);
             auto setId = possibleStates->state_set_id;
             auto possibleStateSize = possibleStates->possible_states_size;
             if (entityType == sensorPdr->entity_type &&
@@ -839,7 +849,7 @@
         while ((record = pldm_pdr_find_record_by_type(
                     repo, PLDM_STATE_SENSOR_PDR, record, &outData, &size)))
         {
-            auto pdr = new (outData) pldm_state_sensor_pdr;
+            auto pdr = std::start_lifetime_as<pldm_state_sensor_pdr>(outData);
             if (pdr && pdr->entity_type == entityType)
             {
                 pdrs.emplace_back(outData, outData + size);
@@ -885,7 +895,7 @@
         while ((record = pldm_pdr_find_record_by_type(
                     repo, PLDM_STATE_EFFECTER_PDR, record, &outData, &size)))
         {
-            auto pdr = new (outData) pldm_state_effecter_pdr;
+            auto pdr = std::start_lifetime_as<pldm_state_effecter_pdr>(outData);
             if (pdr && pdr->entity_type == entityType)
             {
                 pdrs.emplace_back(outData, outData + size);
diff --git a/fw-update/aggregate_update_manager.cpp b/fw-update/aggregate_update_manager.cpp
index c27db95..3bdaacb 100644
--- a/fw-update/aggregate_update_manager.cpp
+++ b/fw-update/aggregate_update_manager.cpp
@@ -1,5 +1,9 @@
 #include "aggregate_update_manager.hpp"
 
+#include "common/start_lifetime_as.hpp"
+
+#include <memory>
+
 namespace pldm::fw_update
 {
 
@@ -8,7 +12,7 @@
 {
     Response response;
     response = UpdateManager::handleRequest(eid, command, request, reqMsgLen);
-    auto responseMsg = new (response.data()) pldm_msg;
+    auto responseMsg = std::start_lifetime_as<pldm_msg>(response.data());
     if (responseMsg->payload[0] != PLDM_FWUP_COMMAND_NOT_EXPECTED)
     {
         return response;
diff --git a/fw-update/test/inventory_manager_test.cpp b/fw-update/test/inventory_manager_test.cpp
index da0dfb7..0b0672f 100644
--- a/fw-update/test/inventory_manager_test.cpp
+++ b/fw-update/test/inventory_manager_test.cpp
@@ -1,3 +1,4 @@
+#include "common/start_lifetime_as.hpp"
 #include "common/utils.hpp"
 #include "fw-update/aggregate_update_manager.hpp"
 #include "fw-update/inventory_manager.hpp"
@@ -5,6 +6,8 @@
 
 #include <libpldm/firmware_update.h>
 
+#include <memory>
+
 #include <gtest/gtest.h>
 
 using namespace pldm;
@@ -143,9 +146,8 @@
     constexpr size_t respPayloadLength = 1;
     constexpr std::array<uint8_t, sizeof(pldm_msg_hdr) + respPayloadLength>
         queryDownstreamIdentifiersResp{0x00, 0x00, 0x00, 0x01};
-    const auto responseMsg =
-        new (const_cast<unsigned char*>(queryDownstreamIdentifiersResp.data()))
-            pldm_msg;
+    const auto responseMsg = std::start_lifetime_as<pldm_msg>(
+        const_cast<unsigned char*>(queryDownstreamIdentifiersResp.data()));
     inventoryManager.queryDownstreamIdentifiers(1, responseMsg,
                                                 respPayloadLength);
 
diff --git a/host-bmc/dbus_to_event_handler.cpp b/host-bmc/dbus_to_event_handler.cpp
index 35132d3..9034e01 100644
--- a/host-bmc/dbus_to_event_handler.cpp
+++ b/host-bmc/dbus_to_event_handler.cpp
@@ -1,10 +1,13 @@
 #include "dbus_to_event_handler.hpp"
 
+#include "common/start_lifetime_as.hpp"
 #include "common/types.hpp"
 #include "libpldmresponder/pdr.hpp"
 
 #include <phosphor-logging/lg2.hpp>
 
+#include <memory>
+
 PHOSPHOR_LOG2_USING;
 
 namespace pldm
@@ -210,7 +213,7 @@
         auto pdrRecord = sensorPDRs.getFirstRecord(pdrEntry);
         while (pdrRecord)
         {
-            pdr = new (pdrEntry.data) pldm_state_sensor_pdr;
+            pdr = std::start_lifetime_as<pldm_state_sensor_pdr>(pdrEntry.data);
             SensorId sensorId = LE16TOH(pdr->sensor_id);
             if (sensorHandlers.contains(pdrType))
             {
diff --git a/host-bmc/host_pdr_handler.cpp b/host-bmc/host_pdr_handler.cpp
index 828e127..24ac3ed 100644
--- a/host-bmc/host_pdr_handler.cpp
+++ b/host-bmc/host_pdr_handler.cpp
@@ -7,6 +7,7 @@
 #ifdef OEM_IBM
 #include <libpldm/oem/ibm/fru.h>
 #endif
+#include "common/start_lifetime_as.hpp"
 #include "dbus/custom_dbus.hpp"
 
 #include <nlohmann/json.hpp>
@@ -18,6 +19,7 @@
 #include <xyz/openbmc_project/State/Host/client.hpp>
 
 #include <cassert>
+#include <memory>
 #include <type_traits>
 
 PHOSPHOR_LOG2_USING;
@@ -563,7 +565,7 @@
                 rh = nextRecordHandle - 1;
             }
 
-            auto pdrHdr = new (pdr.data()) pldm_pdr_hdr;
+            auto pdrHdr = std::start_lifetime_as<pldm_pdr_hdr>(pdr.data());
             if (!rh)
             {
                 rh = pdrHdr->record_handle;
diff --git a/libpldmresponder/platform.cpp b/libpldmresponder/platform.cpp
index a25b89a..5a458d8 100644
--- a/libpldmresponder/platform.cpp
+++ b/libpldmresponder/platform.cpp
@@ -1,5 +1,6 @@
 #include "platform.hpp"
 
+#include "common/start_lifetime_as.hpp"
 #include "common/types.hpp"
 #include "common/utils.hpp"
 #include "event_parser.hpp"
@@ -19,6 +20,8 @@
 
 #include <phosphor-logging/lg2.hpp>
 
+#include <memory>
+
 PHOSPHOR_LOG2_USING;
 
 using namespace pldm::utils;
@@ -867,7 +870,7 @@
     auto pdrRecord = stateSensorPDRs.getFirstRecord(pdrEntry);
     while (pdrRecord)
     {
-        pdr = new (pdrEntry.data) pldm_state_sensor_pdr;
+        pdr = std::start_lifetime_as<pldm_state_sensor_pdr>(pdrEntry.data);
         assert(pdr != nullptr);
         if (pdr->sensor_id != sensorId)
         {
@@ -939,7 +942,7 @@
     auto pdrRecord = stateEffecterPDRs.getFirstRecord(pdrEntry);
     while (pdrRecord)
     {
-        pdr = new (pdrEntry.data) pldm_state_effecter_pdr;
+        pdr = std::start_lifetime_as<pldm_state_effecter_pdr>(pdrEntry.data);
         assert(pdr != nullptr);
         if (pdr->effecter_id != effecterId)
         {
diff --git a/libpldmresponder/platform_numeric_effecter.hpp b/libpldmresponder/platform_numeric_effecter.hpp
index 8bd1f5a..3116542 100644
--- a/libpldmresponder/platform_numeric_effecter.hpp
+++ b/libpldmresponder/platform_numeric_effecter.hpp
@@ -1,5 +1,6 @@
 #pragma once
 
+#include "common/start_lifetime_as.hpp"
 #include "common/utils.hpp"
 #include "libpldmresponder/pdr.hpp"
 #include "pdr_utils.hpp"
@@ -11,6 +12,7 @@
 
 #include <cmath>
 #include <cstdint>
+#include <memory>
 #include <optional>
 
 PHOSPHOR_LOG2_USING;
@@ -273,7 +275,8 @@
     auto pdrRecord = numericEffecterPDRs.getFirstRecord(pdrEntry);
     while (pdrRecord)
     {
-        pdr = new (pdrEntry.data) pldm_numeric_effecter_value_pdr;
+        pdr = std::start_lifetime_as<pldm_numeric_effecter_value_pdr>(
+            pdrEntry.data);
         if (pdr->effecter_id != effecterId)
         {
             pdr = nullptr;
@@ -510,7 +513,8 @@
 
     while (pdrRecord)
     {
-        pdr = new (pdrEntry.data) pldm_numeric_effecter_value_pdr;
+        pdr = std::start_lifetime_as<pldm_numeric_effecter_value_pdr>(
+            pdrEntry.data);
         if (pdr->effecter_id != effecterId)
         {
             pdr = nullptr;
diff --git a/libpldmresponder/platform_state_effecter.hpp b/libpldmresponder/platform_state_effecter.hpp
index cb53561..b782962 100644
--- a/libpldmresponder/platform_state_effecter.hpp
+++ b/libpldmresponder/platform_state_effecter.hpp
@@ -1,5 +1,6 @@
 #pragma once
 
+#include "common/start_lifetime_as.hpp"
 #include "common/utils.hpp"
 #include "libpldmresponder/pdr.hpp"
 #include "pdr_utils.hpp"
@@ -10,6 +11,7 @@
 #include <phosphor-logging/lg2.hpp>
 
 #include <cstdint>
+#include <memory>
 
 PHOSPHOR_LOG2_USING;
 
@@ -66,7 +68,7 @@
     auto pdrRecord = stateEffecterPDRs.getFirstRecord(pdrEntry);
     while (pdrRecord)
     {
-        pdr = new (pdrEntry.data) pldm_state_effecter_pdr;
+        pdr = std::start_lifetime_as<pldm_state_effecter_pdr>(pdrEntry.data);
         if (pdr->effecter_id != effecterId)
         {
             pdr = nullptr;
diff --git a/libpldmresponder/platform_state_sensor.hpp b/libpldmresponder/platform_state_sensor.hpp
index c8e7822..6669ff6 100644
--- a/libpldmresponder/platform_state_sensor.hpp
+++ b/libpldmresponder/platform_state_sensor.hpp
@@ -1,5 +1,6 @@
 #pragma once
 
+#include "common/start_lifetime_as.hpp"
 #include "common/utils.hpp"
 #include "host-bmc/dbus_to_event_handler.hpp"
 #include "libpldmresponder/pdr.hpp"
@@ -12,6 +13,7 @@
 
 #include <cstdint>
 #include <map>
+#include <memory>
 
 PHOSPHOR_LOG2_USING;
 
@@ -108,7 +110,7 @@
     auto pdrRecord = stateSensorPDRs.getFirstRecord(pdrEntry);
     while (pdrRecord)
     {
-        pdr = new (pdrEntry.data) pldm_state_sensor_pdr;
+        pdr = std::start_lifetime_as<pldm_state_sensor_pdr>(pdrEntry.data);
         assert(pdr != nullptr);
         if (pdr->sensor_id != sensorId)
         {
diff --git a/libpldmresponder/test/libpldmresponder_base_test.cpp b/libpldmresponder/test/libpldmresponder_base_test.cpp
index 442ce0c..12b0be2 100644
--- a/libpldmresponder/test/libpldmresponder_base_test.cpp
+++ b/libpldmresponder/test/libpldmresponder_base_test.cpp
@@ -1,3 +1,4 @@
+#include "common/start_lifetime_as.hpp"
 #include "libpldmresponder/base.hpp"
 
 #include <libpldm/base.h>
@@ -6,6 +7,7 @@
 
 #include <array>
 #include <cstring>
+#include <memory>
 
 #include <gtest/gtest.h>
 
@@ -21,14 +23,14 @@
 
 TEST_F(TestBaseCommands, testPLDMTypesGoodRequest)
 {
-    std::array<uint8_t, sizeof(pldm_msg_hdr)> requestPayload{};
-    auto request = new (requestPayload.data()) pldm_msg;
+    std::array<uint8_t, sizeof(pldm_msg)> requestPayload{};
+    auto request = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     // payload length will be 0 in this case
     size_t requestPayloadLength = 0;
     base::Handler handler(event);
     auto response = handler.getPLDMTypes(request, requestPayloadLength);
     // Need to support OEM type.
-    auto responsePtr = new (response.data()) pldm_msg;
+    auto responsePtr = std::start_lifetime_as<pldm_msg>(response.data());
     uint8_t* payload_ptr = responsePtr->payload;
     ASSERT_EQ(payload_ptr[0], 0);
     ASSERT_EQ(payload_ptr[1], 29); // 0b11101 see DSP0240 table11
@@ -40,11 +42,11 @@
     // Need to support OEM type commands.
     std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_COMMANDS_REQ_BYTES>
         requestPayload{};
-    auto request = new (requestPayload.data()) pldm_msg;
+    auto request = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     size_t requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
     base::Handler handler(event);
     auto response = handler.getPLDMCommands(request, requestPayloadLength);
-    auto responsePtr = new (response.data()) pldm_msg;
+    auto responsePtr = std::start_lifetime_as<pldm_msg>(response.data());
     uint8_t* payload_ptr = responsePtr->payload;
     ASSERT_EQ(payload_ptr[0], 0);
     ASSERT_EQ(payload_ptr[1], 60); // 60 = 0b111100
@@ -55,13 +57,13 @@
 {
     std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_COMMANDS_REQ_BYTES>
         requestPayload{};
-    auto request = new (requestPayload.data()) pldm_msg;
+    auto request = std::start_lifetime_as<pldm_msg>(requestPayload.data());
 
     request->payload[0] = 0xFF;
     size_t requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
     base::Handler handler(event);
     auto response = handler.getPLDMCommands(request, requestPayloadLength);
-    auto responsePtr = new (response.data()) pldm_msg;
+    auto responsePtr = std::start_lifetime_as<pldm_msg>(response.data());
     uint8_t* payload_ptr = responsePtr->payload;
     ASSERT_EQ(payload_ptr[0], PLDM_ERROR_INVALID_PLDM_TYPE);
 }
@@ -70,7 +72,7 @@
 {
     std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_VERSION_REQ_BYTES>
         requestPayload{};
-    auto request = new (requestPayload.data()) pldm_msg;
+    auto request = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     size_t requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
 
     uint8_t pldmType = PLDM_BASE;
@@ -86,7 +88,7 @@
 
     base::Handler handler(event);
     auto response = handler.getPLDMVersion(request, requestPayloadLength);
-    auto responsePtr = new (response.data()) pldm_msg;
+    auto responsePtr = std::start_lifetime_as<pldm_msg>(response.data());
 
     ASSERT_EQ(responsePtr->payload[0], 0);
     ASSERT_EQ(0, memcmp(responsePtr->payload + sizeof(responsePtr->payload[0]),
@@ -103,7 +105,7 @@
 {
     std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_VERSION_REQ_BYTES>
         requestPayload{};
-    auto request = new (requestPayload.data()) pldm_msg;
+    auto request = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     size_t requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
 
     uint8_t pldmType = 7;
@@ -117,11 +119,11 @@
 
     base::Handler handler(event);
     auto response = handler.getPLDMVersion(request, requestPayloadLength - 1);
-    auto responsePtr = new (response.data()) pldm_msg;
+    auto responsePtr = std::start_lifetime_as<pldm_msg>(response.data());
 
     ASSERT_EQ(responsePtr->payload[0], PLDM_ERROR_INVALID_LENGTH);
 
-    request = new (requestPayload.data()) pldm_msg;
+    request = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
 
     rc = encode_get_version_req(0, transferHandle, flag, pldmType, request);
@@ -129,22 +131,22 @@
     ASSERT_EQ(0, rc);
 
     response = handler.getPLDMVersion(request, requestPayloadLength);
-    responsePtr = new (response.data()) pldm_msg;
+    responsePtr = std::start_lifetime_as<pldm_msg>(response.data());
 
     ASSERT_EQ(responsePtr->payload[0], PLDM_ERROR_INVALID_PLDM_TYPE);
 }
 
 TEST_F(TestBaseCommands, testGetTIDGoodRequest)
 {
-    std::array<uint8_t, sizeof(pldm_msg_hdr)> requestPayload{};
-    auto request = new (requestPayload.data()) pldm_msg;
+    std::array<uint8_t, sizeof(pldm_msg)> requestPayload{};
+    auto request = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     size_t requestPayloadLength = 0;
 
     base::Handler handler(event);
     handler.setOemPlatformHandler(nullptr);
     auto response = handler.getTID(request, requestPayloadLength);
 
-    auto responsePtr = new (response.data()) pldm_msg;
+    auto responsePtr = std::start_lifetime_as<pldm_msg>(response.data());
     uint8_t* payload = responsePtr->payload;
 
     ASSERT_EQ(payload[0], 0);
diff --git a/libpldmresponder/test/libpldmresponder_pdr_effecter_test.cpp b/libpldmresponder/test/libpldmresponder_pdr_effecter_test.cpp
index e9af77e..4eda681 100644
--- a/libpldmresponder/test/libpldmresponder_pdr_effecter_test.cpp
+++ b/libpldmresponder/test/libpldmresponder_pdr_effecter_test.cpp
@@ -1,3 +1,4 @@
+#include "common/start_lifetime_as.hpp"
 #include "common/test/mocked_utils.hpp"
 #include "common/types.hpp"
 #include "libpldmresponder/pdr_utils.hpp"
@@ -8,6 +9,8 @@
 #include <sdbusplus/test/sdbus_mock.hpp>
 #include <sdeventplus/event.hpp>
 
+#include <memory>
+
 #include <gtest/gtest.h>
 
 using namespace pldm::responder;
@@ -44,7 +47,8 @@
     pdr_utils::PdrEntry e;
     auto record2 = pdr::getRecordByHandle(outRepo, 2, e);
     ASSERT_NE(record2, nullptr);
-    pldm_state_effecter_pdr* pdr = new (e.data) pldm_state_effecter_pdr;
+    pldm_state_effecter_pdr* pdr =
+        std::start_lifetime_as<pldm_state_effecter_pdr>(e.data);
 
     ASSERT_EQ(pdr->hdr.record_handle, 2);
     ASSERT_EQ(pdr->hdr.version, 1);
@@ -61,8 +65,9 @@
     ASSERT_EQ(pdr->effecter_init, PLDM_NO_INIT);
     ASSERT_EQ(pdr->has_description_pdr, false);
     ASSERT_EQ(pdr->composite_effecter_count, 2);
-    state_effecter_possible_states* states = new (pdr->possible_states)
-        state_effecter_possible_states;
+    state_effecter_possible_states* states =
+        std::start_lifetime_as<state_effecter_possible_states>(
+            pdr->possible_states);
     ASSERT_EQ(states->state_set_id, 196);
     ASSERT_EQ(states->possible_states_size, 1);
     bitfield8_t bf1{};
@@ -76,7 +81,7 @@
     // Check second PDR
     auto record3 = pdr::getRecordByHandle(outRepo, 3, e);
     ASSERT_NE(record3, nullptr);
-    pdr = new (e.data) pldm_state_effecter_pdr;
+    pdr = std::start_lifetime_as<pldm_state_effecter_pdr>(e.data);
 
     ASSERT_EQ(pdr->hdr.record_handle, 3);
     ASSERT_EQ(pdr->hdr.version, 1);
@@ -93,13 +98,14 @@
     ASSERT_EQ(pdr->effecter_init, PLDM_NO_INIT);
     ASSERT_EQ(pdr->has_description_pdr, false);
     ASSERT_EQ(pdr->composite_effecter_count, 2);
-    states = new (pdr->possible_states) state_effecter_possible_states;
+    states = std::start_lifetime_as<state_effecter_possible_states>(
+        pdr->possible_states);
     ASSERT_EQ(states->state_set_id, 197);
     ASSERT_EQ(states->possible_states_size, 1);
     bf1.byte = 2;
     ASSERT_EQ(states->states[0].byte, bf1.byte);
-    states = new (pdr->possible_states + sizeof(state_effecter_possible_states))
-        state_effecter_possible_states;
+    states = std::start_lifetime_as<state_effecter_possible_states>(
+        pdr->possible_states + sizeof(state_effecter_possible_states));
     ASSERT_EQ(states->state_set_id, 198);
     ASSERT_EQ(states->possible_states_size, 2);
     bitfield8_t bf2[2];
@@ -144,8 +150,8 @@
     auto record = pdr::getRecordByHandle(outRepo, 4, e);
     ASSERT_NE(record, nullptr);
 
-    pldm_numeric_effecter_value_pdr* pdr = new (e.data)
-        pldm_numeric_effecter_value_pdr;
+    pldm_numeric_effecter_value_pdr* pdr =
+        std::start_lifetime_as<pldm_numeric_effecter_value_pdr>(e.data);
     EXPECT_EQ(pdr->hdr.record_handle, 4);
     EXPECT_EQ(pdr->hdr.version, 1);
     EXPECT_EQ(pdr->hdr.type, PLDM_NUMERIC_EFFECTER_PDR);
diff --git a/libpldmresponder/test/libpldmresponder_pdr_sensor_test.cpp b/libpldmresponder/test/libpldmresponder_pdr_sensor_test.cpp
index f8e0a05..0e98ff2 100644
--- a/libpldmresponder/test/libpldmresponder_pdr_sensor_test.cpp
+++ b/libpldmresponder/test/libpldmresponder_pdr_sensor_test.cpp
@@ -1,3 +1,4 @@
+#include "common/start_lifetime_as.hpp"
 #include "common/test/mocked_utils.hpp"
 #include "libpldmresponder/pdr_utils.hpp"
 #include "libpldmresponder/platform.hpp"
@@ -7,6 +8,8 @@
 #include <sdbusplus/test/sdbus_mock.hpp>
 #include <sdeventplus/event.hpp>
 
+#include <memory>
+
 #include <gtest/gtest.h>
 
 using namespace pldm::responder;
@@ -22,7 +25,7 @@
 {
     std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_PDR_REQ_BYTES>
         requestPayload{};
-    auto req = new (requestPayload.data()) pldm_msg;
+    auto req = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     size_t requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
 
     MockdBusHandler mockedUtils;
@@ -49,7 +52,8 @@
     auto record = pdr::getRecordByHandle(outRepo, 2, e);
     ASSERT_NE(record, nullptr);
 
-    pldm_state_sensor_pdr* pdr = new (e.data) pldm_state_sensor_pdr;
+    pldm_state_sensor_pdr* pdr =
+        std::start_lifetime_as<pldm_state_sensor_pdr>(e.data);
     EXPECT_EQ(pdr->hdr.record_handle, 2);
     EXPECT_EQ(pdr->hdr.version, 1);
     EXPECT_EQ(pdr->hdr.type, PLDM_STATE_SENSOR_PDR);
@@ -73,7 +77,7 @@
 {
     std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_PDR_REQ_BYTES>
         requestPayload{};
-    auto req = new (requestPayload.data()) pldm_msg;
+    auto req = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     size_t requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
 
     MockdBusHandler mockedUtils;
diff --git a/libpldmresponder/test/libpldmresponder_platform_test.cpp b/libpldmresponder/test/libpldmresponder_platform_test.cpp
index 7b7c82b..294ae81 100644
--- a/libpldmresponder/test/libpldmresponder_platform_test.cpp
+++ b/libpldmresponder/test/libpldmresponder_platform_test.cpp
@@ -1,3 +1,4 @@
+#include "common/start_lifetime_as.hpp"
 #include "common/test/mocked_utils.hpp"
 #include "common/types.hpp"
 #include "common/utils.hpp"
@@ -13,6 +14,8 @@
 #include <sdbusplus/test/sdbus_mock.hpp>
 #include <sdeventplus/event.hpp>
 
+#include <memory>
+
 using namespace pldm::pdr;
 using namespace pldm::utils;
 using namespace pldm::responder;
@@ -28,10 +31,11 @@
 {
     std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_PDR_REQ_BYTES>
         requestPayload{};
-    auto req = new (requestPayload.data()) pldm_msg;
+    auto req = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     size_t requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
 
-    struct pldm_get_pdr_req* request = new (req->payload) pldm_get_pdr_req;
+    struct pldm_get_pdr_req* request =
+        std::start_lifetime_as<pldm_get_pdr_req>(req->payload);
     request->request_count = 100;
 
     MockdBusHandler mockedUtils;
@@ -47,15 +51,15 @@
     Repo repo(pdrRepo);
     ASSERT_EQ(repo.empty(), false);
     auto response = handler.getPDR(req, requestPayloadLength);
-    auto responsePtr = new (response.data()) pldm_msg;
+    auto responsePtr = std::start_lifetime_as<pldm_msg>(response.data());
 
-    struct pldm_get_pdr_resp* resp = new (responsePtr->payload)
-        pldm_get_pdr_resp;
+    struct pldm_get_pdr_resp* resp =
+        std::start_lifetime_as<pldm_get_pdr_resp>(responsePtr->payload);
     ASSERT_EQ(PLDM_SUCCESS, resp->completion_code);
     ASSERT_EQ(2, resp->next_record_handle);
     ASSERT_EQ(true, resp->response_count != 0);
 
-    pldm_pdr_hdr* hdr = new (resp->record_data) pldm_pdr_hdr;
+    pldm_pdr_hdr* hdr = std::start_lifetime_as<pldm_pdr_hdr>(resp->record_data);
     ASSERT_EQ(hdr->record_handle, 1);
     ASSERT_EQ(hdr->version, 1);
 
@@ -66,10 +70,11 @@
 {
     std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_PDR_REQ_BYTES>
         requestPayload{};
-    auto req = new (requestPayload.data()) pldm_msg;
+    auto req = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     size_t requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
 
-    struct pldm_get_pdr_req* request = new (req->payload) pldm_get_pdr_req;
+    struct pldm_get_pdr_req* request =
+        std::start_lifetime_as<pldm_get_pdr_req>(req->payload);
     request->request_count = 1;
 
     MockdBusHandler mockedUtils;
@@ -85,9 +90,9 @@
     Repo repo(pdrRepo);
     ASSERT_EQ(repo.empty(), false);
     auto response = handler.getPDR(req, requestPayloadLength);
-    auto responsePtr = new (response.data()) pldm_msg;
-    struct pldm_get_pdr_resp* resp = new (responsePtr->payload)
-        pldm_get_pdr_resp;
+    auto responsePtr = std::start_lifetime_as<pldm_msg>(response.data());
+    struct pldm_get_pdr_resp* resp =
+        std::start_lifetime_as<pldm_get_pdr_resp>(responsePtr->payload);
     ASSERT_EQ(PLDM_SUCCESS, resp->completion_code);
     ASSERT_EQ(1, resp->response_count);
     pldm_pdr_destroy(pdrRepo);
@@ -97,10 +102,11 @@
 {
     std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_PDR_REQ_BYTES>
         requestPayload{};
-    auto req = new (requestPayload.data()) pldm_msg;
+    auto req = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     size_t requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
 
-    struct pldm_get_pdr_req* request = new (req->payload) pldm_get_pdr_req;
+    struct pldm_get_pdr_req* request =
+        std::start_lifetime_as<pldm_get_pdr_req>(req->payload);
     request->record_handle = 100000;
     request->request_count = 1;
 
@@ -117,7 +123,7 @@
     Repo repo(pdrRepo);
     ASSERT_EQ(repo.empty(), false);
     auto response = handler.getPDR(req, requestPayloadLength);
-    auto responsePtr = new (response.data()) pldm_msg;
+    auto responsePtr = std::start_lifetime_as<pldm_msg>(response.data());
 
     ASSERT_EQ(responsePtr->payload[0], PLDM_PLATFORM_INVALID_RECORD_HANDLE);
 
@@ -128,10 +134,11 @@
 {
     std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_PDR_REQ_BYTES>
         requestPayload{};
-    auto req = new (requestPayload.data()) pldm_msg;
+    auto req = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     size_t requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
 
-    struct pldm_get_pdr_req* request = new (req->payload) pldm_get_pdr_req;
+    struct pldm_get_pdr_req* request =
+        std::start_lifetime_as<pldm_get_pdr_req>(req->payload);
     request->record_handle = 1;
 
     MockdBusHandler mockedUtils;
@@ -147,9 +154,9 @@
     Repo repo(pdrRepo);
     ASSERT_EQ(repo.empty(), false);
     auto response = handler.getPDR(req, requestPayloadLength);
-    auto responsePtr = new (response.data()) pldm_msg;
-    struct pldm_get_pdr_resp* resp = new (responsePtr->payload)
-        pldm_get_pdr_resp;
+    auto responsePtr = std::start_lifetime_as<pldm_msg>(response.data());
+    struct pldm_get_pdr_resp* resp =
+        std::start_lifetime_as<pldm_get_pdr_resp>(responsePtr->payload);
     ASSERT_EQ(PLDM_SUCCESS, resp->completion_code);
     ASSERT_EQ(2, resp->next_record_handle);
 
@@ -160,10 +167,11 @@
 {
     std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_PDR_REQ_BYTES>
         requestPayload{};
-    auto req = new (requestPayload.data()) pldm_msg;
+    auto req = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     size_t requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
 
-    struct pldm_get_pdr_req* request = new (req->payload) pldm_get_pdr_req;
+    struct pldm_get_pdr_req* request =
+        std::start_lifetime_as<pldm_get_pdr_req>(req->payload);
     request->request_count = 100;
 
     MockdBusHandler mockedUtils;
@@ -188,19 +196,20 @@
     {
         request->record_handle = handle;
         auto response = handler.getPDR(req, requestPayloadLength);
-        auto responsePtr = new (response.data()) pldm_msg;
-        struct pldm_get_pdr_resp* resp = new (responsePtr->payload)
-            pldm_get_pdr_resp;
+        auto responsePtr = std::start_lifetime_as<pldm_msg>(response.data());
+        struct pldm_get_pdr_resp* resp =
+            std::start_lifetime_as<pldm_get_pdr_resp>(responsePtr->payload);
         ASSERT_EQ(PLDM_SUCCESS, resp->completion_code);
 
-        handle = resp->next_record_handle; // point to the next pdr in case
-                                           // current is not what we want
+        handle = resp->next_record_handle;
 
-        pldm_pdr_hdr* hdr = new (resp->record_data) pldm_pdr_hdr;
+        pldm_pdr_hdr* hdr =
+            std::start_lifetime_as<pldm_pdr_hdr>(resp->record_data);
         if (hdr->type == PLDM_STATE_EFFECTER_PDR)
         {
-            pldm_state_effecter_pdr* pdr = new (resp->record_data)
-                pldm_state_effecter_pdr;
+            pldm_state_effecter_pdr* pdr =
+                std::start_lifetime_as<pldm_state_effecter_pdr>(
+                    resp->record_data);
             if (pdr->entity_type == 100)
             {
                 found = true;
@@ -222,7 +231,7 @@
 {
     std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_PDR_REQ_BYTES>
         requestPayload{};
-    auto req = new (requestPayload.data()) pldm_msg;
+    auto req = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     size_t requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
 
     MockdBusHandler mockedUtils;
@@ -243,7 +252,8 @@
     pdr_utils::PdrEntry e;
     auto record1 = pdr::getRecordByHandle(outRepo, 2, e);
     ASSERT_NE(record1, nullptr);
-    pldm_state_effecter_pdr* pdr = new (e.data) pldm_state_effecter_pdr;
+    pldm_state_effecter_pdr* pdr =
+        std::start_lifetime_as<pldm_state_effecter_pdr>(e.data);
     EXPECT_EQ(pdr->hdr.type, PLDM_STATE_EFFECTER_PDR);
 
     std::vector<set_effecter_state_field> stateField;
@@ -269,7 +279,7 @@
 {
     std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_PDR_REQ_BYTES>
         requestPayload{};
-    auto req = new (requestPayload.data()) pldm_msg;
+    auto req = std::start_lifetime_as<pldm_msg>(requestPayload.data());
     size_t requestPayloadLength = requestPayload.size() - sizeof(pldm_msg_hdr);
 
     MockdBusHandler mockedUtils;
@@ -290,7 +300,8 @@
     pdr_utils::PdrEntry e;
     auto record1 = pdr::getRecordByHandle(outRepo, 2, e);
     ASSERT_NE(record1, nullptr);
-    pldm_state_effecter_pdr* pdr = new (e.data) pldm_state_effecter_pdr;
+    pldm_state_effecter_pdr* pdr =
+        std::start_lifetime_as<pldm_state_effecter_pdr>(e.data);
     EXPECT_EQ(pdr->hdr.type, PLDM_STATE_EFFECTER_PDR);
 
     std::vector<set_effecter_state_field> stateField;
@@ -335,8 +346,8 @@
     auto record4 = pdr::getRecordByHandle(numericEffecterPDRs, 4, e);
     ASSERT_NE(record4, nullptr);
 
-    pldm_numeric_effecter_value_pdr* pdr = new (e.data)
-        pldm_numeric_effecter_value_pdr;
+    pldm_numeric_effecter_value_pdr* pdr =
+        std::start_lifetime_as<pldm_numeric_effecter_value_pdr>(e.data);
     EXPECT_EQ(pdr->hdr.type, PLDM_NUMERIC_EFFECTER_PDR);
 
     uint16_t effecterId = 3;
@@ -379,8 +390,8 @@
     auto record4 = pdr::getRecordByHandle(numericEffecterPDRs, 4, e);
     ASSERT_NE(record4, nullptr);
 
-    pldm_numeric_effecter_value_pdr* pdr = new (e.data)
-        pldm_numeric_effecter_value_pdr;
+    pldm_numeric_effecter_value_pdr* pdr =
+        std::start_lifetime_as<pldm_numeric_effecter_value_pdr>(e.data);
     EXPECT_EQ(pdr->hdr.type, PLDM_NUMERIC_EFFECTER_PDR);
 
     uint16_t effecterId = 3;
@@ -416,8 +427,8 @@
     auto record4 = pdr::getRecordByHandle(numericEffecterPDRs, 4, e);
     ASSERT_NE(record4, nullptr);
 
-    pldm_numeric_effecter_value_pdr* pdr = new (e.data)
-        pldm_numeric_effecter_value_pdr;
+    pldm_numeric_effecter_value_pdr* pdr =
+        std::start_lifetime_as<pldm_numeric_effecter_value_pdr>(e.data);
     EXPECT_EQ(pdr->hdr.type, PLDM_NUMERIC_EFFECTER_PDR);
 
     uint16_t effecterId = 3;
@@ -449,7 +460,7 @@
         getEffecterDataSize(effecterDataSize);
 
     Response response(responsePayloadLength + sizeof(pldm_msg_hdr));
-    auto responsePtr = new (response.data()) pldm_msg;
+    auto responsePtr = std::start_lifetime_as<pldm_msg>(response.data());
 
     rc = platform_numeric_effecter::getNumericEffecterValueHandler(
         propertyType, dbusValue, effecterDataSize, responsePtr,
@@ -458,7 +469,8 @@
     ASSERT_EQ(rc, 0);
 
     struct pldm_get_numeric_effecter_value_resp* resp =
-        new (responsePtr->payload) pldm_get_numeric_effecter_value_resp;
+        std::start_lifetime_as<pldm_get_numeric_effecter_value_resp>(
+            responsePtr->payload);
     ASSERT_EQ(PLDM_SUCCESS, resp->completion_code);
     uint32_t valPresent = 0;
     memcpy(&valPresent, &resp->pending_and_present_values[4],
@@ -491,8 +503,8 @@
     auto record4 = pdr::getRecordByHandle(numericEffecterPDRs, 4, e);
     ASSERT_NE(record4, nullptr);
 
-    pldm_numeric_effecter_value_pdr* pdr = new (e.data)
-        pldm_numeric_effecter_value_pdr;
+    pldm_numeric_effecter_value_pdr* pdr =
+        std::start_lifetime_as<pldm_numeric_effecter_value_pdr>(e.data);
     EXPECT_EQ(pdr->hdr.type, PLDM_NUMERIC_EFFECTER_PDR);
 
     uint16_t effecterId = 4;
@@ -791,7 +803,8 @@
     pdr_utils::PdrEntry e;
     auto record = pdr::getRecordByHandle(outRepo, 2, e);
     ASSERT_NE(record, nullptr);
-    pldm_state_sensor_pdr* pdr = new (e.data) pldm_state_sensor_pdr;
+    pldm_state_sensor_pdr* pdr =
+        std::start_lifetime_as<pldm_state_sensor_pdr>(e.data);
     EXPECT_EQ(pdr->hdr.type, PLDM_STATE_SENSOR_PDR);
 
     std::vector<get_sensor_state_field> stateField;
@@ -840,7 +853,8 @@
     pdr_utils::PdrEntry e;
     auto record = pdr::getRecordByHandle(outRepo, 2, e);
     ASSERT_NE(record, nullptr);
-    pldm_state_sensor_pdr* pdr = new (e.data) pldm_state_sensor_pdr;
+    pldm_state_sensor_pdr* pdr =
+        std::start_lifetime_as<pldm_state_sensor_pdr>(e.data);
     EXPECT_EQ(pdr->hdr.type, PLDM_STATE_SENSOR_PDR);
 
     std::vector<get_sensor_state_field> stateField;
diff --git a/platform-mc/platform_manager.cpp b/platform-mc/platform_manager.cpp
index b6c9d81..bb90053 100644
--- a/platform-mc/platform_manager.cpp
+++ b/platform-mc/platform_manager.cpp
@@ -1,11 +1,14 @@
 #include "platform_manager.hpp"
 
+#include "common/start_lifetime_as.hpp"
 #include "common/types.hpp"
 #include "manager.hpp"
 #include "terminus_manager.hpp"
 
 #include <phosphor-logging/lg2.hpp>
 
+#include <memory>
+
 PHOSPHOR_LOG2_USING;
 
 namespace pldm
@@ -356,7 +359,7 @@
         {
             // multipart transfer
             uint32_t receivedRecordSize = responseCnt;
-            auto pdrHdr = new (recvBuf.data()) pldm_pdr_hdr;
+            auto pdrHdr = std::start_lifetime_as<pldm_pdr_hdr>(recvBuf.data());
             uint16_t recordChgNum = le16toh(pdrHdr->record_change_num);
             std::vector<uint8_t> receivedPdr(recvBuf.begin(),
                                              recvBuf.begin() + responseCnt);
diff --git a/platform-mc/terminus.cpp b/platform-mc/terminus.cpp
index 2afbbc7..b536b0c 100644
--- a/platform-mc/terminus.cpp
+++ b/platform-mc/terminus.cpp
@@ -1,11 +1,13 @@
 #include "terminus.hpp"
 
+#include "common/start_lifetime_as.hpp"
 #include "dbus_impl_fru.hpp"
 
 #include <libpldm/platform.h>
 
 #include <common/utils.hpp>
 
+#include <memory>
 #include <ranges>
 
 namespace pldm
@@ -141,7 +143,7 @@
 {
     for (auto& pdr : pdrs)
     {
-        auto pdrHdr = new (pdr.data()) pldm_pdr_hdr;
+        auto pdrHdr = std::start_lifetime_as<pldm_pdr_hdr>(pdr.data());
         switch (pdrHdr->type)
         {
             case PLDM_SENSOR_AUXILIARY_NAMES_PDR:
@@ -381,7 +383,8 @@
     size_t decodedPdrSize =
         sizeof(struct pldm_entity_auxiliary_names_pdr) + names_size;
     auto vPdr = std::vector<char>(decodedPdrSize);
-    auto decodedPdr = new (vPdr.data()) pldm_entity_auxiliary_names_pdr;
+    auto decodedPdr =
+        std::start_lifetime_as<pldm_entity_auxiliary_names_pdr>(vPdr.data());
 
     auto rc = decode_entity_auxiliary_names_pdr(pdrData.data(), pdrData.size(),
                                                 decodedPdr, decodedPdrSize);
diff --git a/pldmtool/oem/ibm/pldm_oem_ibm.cpp b/pldmtool/oem/ibm/pldm_oem_ibm.cpp
index c260614..9f8827b 100644
--- a/pldmtool/oem/ibm/pldm_oem_ibm.cpp
+++ b/pldmtool/oem/ibm/pldm_oem_ibm.cpp
@@ -1,6 +1,7 @@
 #include "pldm_oem_ibm.hpp"
 
 #include "../../pldm_cmd_helper.hpp"
+#include "common/start_lifetime_as.hpp"
 
 #include <endian.h>
 #include <libpldm/oem/ibm/file_io.h>
@@ -8,6 +9,7 @@
 #include <libpldm/pldm_types.h>
 
 #include <iostream>
+#include <memory>
 #include <string>
 namespace pldmtool
 {
@@ -170,7 +172,8 @@
         while (startptr < endptr)
         {
             ordered_json fdata;
-            auto filetableData = new (startptr) pldm_file_attr_table_entry;
+            auto filetableData =
+                std::start_lifetime_as<pldm_file_attr_table_entry>(startptr);
             fdata["FileHandle"] = std::to_string(filetableData->file_handle);
             startptr += sizeof(filetableData->file_handle);
 
diff --git a/pldmtool/pldm_platform_cmd.cpp b/pldmtool/pldm_platform_cmd.cpp
index 5bc01ac..00f7af9 100644
--- a/pldmtool/pldm_platform_cmd.cpp
+++ b/pldmtool/pldm_platform_cmd.cpp
@@ -1,3 +1,4 @@
+#include "common/start_lifetime_as.hpp"
 #include "common/types.hpp"
 #include "common/utils.hpp"
 #include "pldm_cmd_helper.hpp"
@@ -619,8 +620,8 @@
             {
                 nextPartRequired = true;
                 dataTransferHandle = nextDataTransferHndl;
-                struct pldm_pdr_hdr* pdr_hdr = new (recordData.data())
-                    pldm_pdr_hdr;
+                struct pldm_pdr_hdr* pdr_hdr =
+                    std::start_lifetime_as<pldm_pdr_hdr>(recordData.data());
                 recordChangeNumber = pdr_hdr->record_change_num;
                 operationFlag = PLDM_GET_NEXTPART;
             }
@@ -1252,7 +1253,8 @@
         }
 
         data += sizeof(pldm_pdr_hdr);
-        pldm_pdr_fru_record_set* pdr = new (data) pldm_pdr_fru_record_set;
+        pldm_pdr_fru_record_set* pdr =
+            std::start_lifetime_as<pldm_pdr_fru_record_set>(data);
         if (!pdr)
         {
             std::cerr << "Failed to get the FRU record set PDR" << std::endl;
@@ -1279,8 +1281,8 @@
         }
 
         data += sizeof(pldm_pdr_hdr);
-        pldm_pdr_entity_association* pdr = new (data)
-            pldm_pdr_entity_association;
+        pldm_pdr_entity_association* pdr =
+            std::start_lifetime_as<pldm_pdr_entity_association>(data);
         if (!pdr)
         {
             std::cerr << "Failed to get the PDR eneity association"
diff --git a/requester/test/handler_test.cpp b/requester/test/handler_test.cpp
index 000ddea..37be41c 100644
--- a/requester/test/handler_test.cpp
+++ b/requester/test/handler_test.cpp
@@ -1,4 +1,5 @@
 #include "common/instance_id.hpp"
+#include "common/start_lifetime_as.hpp"
 #include "common/types.hpp"
 #include "common/utils.hpp"
 #include "mock_request.hpp"
@@ -10,6 +11,8 @@
 
 #include <sdbusplus/async.hpp>
 
+#include <memory>
+
 #include <gmock/gmock.h>
 #include <gtest/gtest.h>
 
@@ -260,8 +263,8 @@
                                               mctp_eid_t eid,
                                               uint8_t instanceId, uint8_t& tid)
         {
-            pldm::Request request(sizeof(pldm_msg_hdr), 0);
-            auto requestMsg = new (request.data()) pldm_msg;
+            pldm::Request request(sizeof(pldm_msg), 0);
+            auto requestMsg = std::start_lifetime_as<pldm_msg>(request.data());
             const pldm_msg* responseMsg = nullptr;
             size_t responseLen = 0;
 
diff --git a/softoff/softoff.cpp b/softoff/softoff.cpp
index 3162721..a14a5b4 100644
--- a/softoff/softoff.cpp
+++ b/softoff/softoff.cpp
@@ -1,6 +1,7 @@
 #include "softoff.hpp"
 
 #include "common/instance_id.hpp"
+#include "common/start_lifetime_as.hpp"
 #include "common/transport.hpp"
 #include "common/utils.hpp"
 
@@ -19,6 +20,7 @@
 #include <array>
 #include <filesystem>
 #include <fstream>
+#include <memory>
 
 PHOSPHOR_LOG2_USING;
 
@@ -190,7 +192,8 @@
         {
             for (auto& rep : response)
             {
-                auto softoffPdr = new (rep.data()) pldm_state_effecter_pdr;
+                auto softoffPdr =
+                    std::start_lifetime_as<pldm_state_effecter_pdr>(rep.data());
                 effecterID = softoffPdr->effecter_id;
             }
         }
@@ -232,7 +235,7 @@
         pldm_state_sensor_pdr* pdr = nullptr;
         for (auto& rep : Response)
         {
-            pdr = new (rep.data()) pldm_state_sensor_pdr;
+            pdr = std::start_lifetime_as<pldm_state_sensor_pdr>(rep.data());
             if (!pdr)
             {
                 error("Failed to get state sensor PDR.");
@@ -247,8 +250,9 @@
 
         for (auto offset = 0; offset < compositeSensorCount; offset++)
         {
-            auto possibleStates = new (possibleStatesStart)
-                state_sensor_possible_states;
+            auto possibleStates =
+                std::start_lifetime_as<state_sensor_possible_states>(
+                    possibleStatesStart);
             auto setId = possibleStates->state_set_id;
             auto possibleStateSize = possibleStates->possible_states_size;
 
@@ -301,7 +305,7 @@
                sizeof(pldm_msg_hdr) + sizeof(effecterID) +
                    sizeof(effecterCount) + sizeof(set_effecter_state_field)>
         requestMsg{};
-    auto request = new (requestMsg.data()) pldm_msg;
+    auto request = std::start_lifetime_as<pldm_msg>(requestMsg.data());
     set_effecter_state_field stateField{PLDM_REQUEST_SET, effecterState};
     auto instanceIdResult = instanceIdDb.next(pldmTID);
     if (!instanceIdResult)
@@ -367,7 +371,7 @@
         // We've got the response meant for the PLDM request msg that was
         // sent out
         io.set_enabled(Enabled::Off);
-        auto response = new (responseMsgPtr.get()) pldm_msg;
+        auto response = std::start_lifetime_as<pldm_msg>(responseMsgPtr.get());
 
         if (srcTID != pldmTID ||
             !pldm_msg_hdr_correlate_response(&request->hdr, &response->hdr))