blob: f2238192c230403a347f5b4aea875f9604957fef [file] [log] [blame]
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +05301#include "file_io.hpp"
2
Sampa Misra854e61f2019-08-22 04:36:47 -05003#include "file_io_by_type.hpp"
Tom Joseph0c6d22c2019-06-26 09:58:41 +05304#include "file_table.hpp"
Ravi Tejace1c96f2020-10-05 23:13:01 -05005#include "utils.hpp"
Sampa Misra854e61f2019-08-22 04:36:47 -05006#include "xyz/openbmc_project/Common/error.hpp"
Jinu Joy Thomasf666db12019-05-29 05:22:31 -05007
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +05308#include <fcntl.h>
George Liuc453e162022-12-21 17:16:23 +08009#include <libpldm/base.h>
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +053010#include <sys/mman.h>
11#include <sys/stat.h>
12#include <sys/types.h>
13#include <unistd.h>
14
Riya Dixit49cfb132023-03-02 04:26:53 -060015#include <phosphor-logging/lg2.hpp>
16
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +053017#include <cstring>
18#include <fstream>
Sampa Misra854e61f2019-08-22 04:36:47 -050019#include <memory>
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +053020
Riya Dixit49cfb132023-03-02 04:26:53 -060021PHOSPHOR_LOG2_USING;
22
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +053023namespace pldm
24{
Ravi Tejace1c96f2020-10-05 23:13:01 -050025using namespace pldm::responder::utils;
Sampa Misra854e61f2019-08-22 04:36:47 -050026using namespace sdbusplus::xyz::openbmc_project::Common::Error;
27
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +053028namespace responder
29{
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +053030namespace fs = std::filesystem;
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +053031
32namespace dma
33{
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +053034/** @struct AspeedXdmaOp
35 *
36 * Structure representing XDMA operation
37 */
38struct AspeedXdmaOp
39{
40 uint64_t hostAddr; //!< the DMA address on the host side, configured by
41 //!< PCI subsystem.
42 uint32_t len; //!< the size of the transfer in bytes, it should be a
43 //!< multiple of 16 bytes
44 uint32_t upstream; //!< boolean indicating the direction of the DMA
45 //!< operation, true means a transfer from BMC to host.
46};
47
Deepak Kodihalli134cc1b2019-10-04 01:51:02 -050048constexpr auto xdmaDev = "/dev/aspeed-xdma";
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +053049
Ravi Tejace1c96f2020-10-05 23:13:01 -050050int DMA::transferHostDataToSocket(int fd, uint32_t length, uint64_t address)
51{
52 static const size_t pageSize = getpagesize();
53 uint32_t numPages = length / pageSize;
54 uint32_t pageAlignedLength = numPages * pageSize;
55
56 if (length > pageAlignedLength)
57 {
58 pageAlignedLength += pageSize;
59 }
60
61 auto mmapCleanup = [pageAlignedLength](void* vgaMem) {
62 munmap(vgaMem, pageAlignedLength);
63 };
64
65 int dmaFd = -1;
66 int rc = 0;
67 dmaFd = open(xdmaDev, O_RDWR);
68 if (dmaFd < 0)
69 {
70 rc = -errno;
Riya Dixit49cfb132023-03-02 04:26:53 -060071 error(
Riya Dixitfc84f632024-04-06 14:00:02 -050072 "Failed to open the XDMA device for transferring remote terminus data to socket with response code '{RC}'",
Riya Dixit49cfb132023-03-02 04:26:53 -060073 "RC", rc);
Ravi Tejace1c96f2020-10-05 23:13:01 -050074 return rc;
75 }
76
77 pldm::utils::CustomFD xdmaFd(dmaFd);
78
79 void* vgaMem;
Patrick Williams16c2a0a2024-08-16 15:20:59 -040080 vgaMem =
81 mmap(nullptr, pageAlignedLength, PROT_READ, MAP_SHARED, xdmaFd(), 0);
Ravi Tejace1c96f2020-10-05 23:13:01 -050082 if (MAP_FAILED == vgaMem)
83 {
84 rc = -errno;
Riya Dixit49cfb132023-03-02 04:26:53 -060085 error(
Riya Dixitfc84f632024-04-06 14:00:02 -050086 "Failed to mmap the XDMA device for transferring remote terminus data to socket with response code '{RC}'",
Riya Dixit49cfb132023-03-02 04:26:53 -060087 "RC", rc);
Ravi Tejace1c96f2020-10-05 23:13:01 -050088 return rc;
89 }
90
91 std::unique_ptr<void, decltype(mmapCleanup)> vgaMemPtr(vgaMem, mmapCleanup);
92
93 AspeedXdmaOp xdmaOp;
94 xdmaOp.upstream = 0;
95 xdmaOp.hostAddr = address;
96 xdmaOp.len = length;
97
98 rc = write(xdmaFd(), &xdmaOp, sizeof(xdmaOp));
99 if (rc < 0)
100 {
101 rc = -errno;
Riya Dixit49cfb132023-03-02 04:26:53 -0600102 error(
Manojkiran Eda2576aec2024-06-17 12:05:17 +0530103 "Failed to execute the DMA operation for transferring remote terminus data to socket at address '{ADDRESS}' and length '{LENGTH}' with response code '{RC}'",
Riya Dixitfc84f632024-04-06 14:00:02 -0500104 "RC", rc, "ADDRESS", address, "LENGTH", length);
Ravi Tejace1c96f2020-10-05 23:13:01 -0500105 return rc;
106 }
107
108 rc = writeToUnixSocket(fd, static_cast<const char*>(vgaMemPtr.get()),
109 length);
110 if (rc < 0)
111 {
112 rc = -errno;
113 close(fd);
Riya Dixit49cfb132023-03-02 04:26:53 -0600114 error(
Manojkiran Eda2576aec2024-06-17 12:05:17 +0530115 "Failed to write to Unix socket, closing socket for transferring remote terminus data to socket with response code '{RC}'",
Riya Dixit49cfb132023-03-02 04:26:53 -0600116 "RC", rc);
Ravi Tejace1c96f2020-10-05 23:13:01 -0500117 return rc;
118 }
119 return 0;
120}
121
Deepak Kodihalli15211b42019-12-14 02:24:49 -0600122int DMA::transferDataHost(int fd, uint32_t offset, uint32_t length,
123 uint64_t address, bool upstream)
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530124{
125 static const size_t pageSize = getpagesize();
126 uint32_t numPages = length / pageSize;
127 uint32_t pageAlignedLength = numPages * pageSize;
128
129 if (length > pageAlignedLength)
130 {
131 pageAlignedLength += pageSize;
132 }
133
ArchanaKakani93409752022-04-19 00:36:04 -0500134 int rc = 0;
135 auto mmapCleanup = [pageAlignedLength, &rc](void* vgaMem) {
136 if (rc != -EINTR)
137 {
138 munmap(vgaMem, pageAlignedLength);
139 }
140 else
141 {
Riya Dixit49cfb132023-03-02 04:26:53 -0600142 error(
Riya Dixitfc84f632024-04-06 14:00:02 -0500143 "Received interrupt during DMA transfer for data between BMC and remote terminus. Skipping Unmap.");
ArchanaKakani93409752022-04-19 00:36:04 -0500144 }
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530145 };
146
Deepak Kodihalli15211b42019-12-14 02:24:49 -0600147 int dmaFd = -1;
Deepak Kodihalli15211b42019-12-14 02:24:49 -0600148 dmaFd = open(xdmaDev, O_RDWR);
149 if (dmaFd < 0)
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530150 {
151 rc = -errno;
Riya Dixitfc84f632024-04-06 14:00:02 -0500152 error(
153 "Failed to open the XDMA device for data transfer between BMC and remote terminus with response code '{RC}'",
154 "RC", rc);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530155 return rc;
156 }
157
George Liu83409572019-12-24 18:42:54 +0800158 pldm::utils::CustomFD xdmaFd(dmaFd);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530159
160 void* vgaMem;
161 vgaMem = mmap(nullptr, pageAlignedLength, upstream ? PROT_WRITE : PROT_READ,
162 MAP_SHARED, xdmaFd(), 0);
163 if (MAP_FAILED == vgaMem)
164 {
165 rc = -errno;
Riya Dixitfc84f632024-04-06 14:00:02 -0500166 error(
167 "Failed to mmap the XDMA device for data transfer between BMC and remote terminus with response code '{RC}'",
168 "RC", rc);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530169 return rc;
170 }
171
172 std::unique_ptr<void, decltype(mmapCleanup)> vgaMemPtr(vgaMem, mmapCleanup);
173
174 if (upstream)
175 {
Deepak Kodihalli15211b42019-12-14 02:24:49 -0600176 rc = lseek(fd, offset, SEEK_SET);
177 if (rc == -1)
178 {
Riya Dixit49cfb132023-03-02 04:26:53 -0600179 error(
Riya Dixitfc84f632024-04-06 14:00:02 -0500180 "Failed to transfer data between BMC and remote terminus due to lseek failure with upstream '{UPSTREAM}' at offset '{OFFSET}', error number - {ERROR_NUM}",
181 "ERROR_NUM", errno, "UPSTREAM", upstream, "OFFSET", offset);
Deepak Kodihalli15211b42019-12-14 02:24:49 -0600182 return rc;
183 }
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530184
185 // Writing to the VGA memory should be aligned at page boundary,
186 // otherwise write data into a buffer aligned at page boundary and
187 // then write to the VGA memory.
188 std::vector<char> buffer{};
189 buffer.resize(pageAlignedLength);
Deepak Kodihalli15211b42019-12-14 02:24:49 -0600190 rc = read(fd, buffer.data(), length);
191 if (rc == -1)
192 {
Riya Dixit49cfb132023-03-02 04:26:53 -0600193 error(
Riya Dixitfc84f632024-04-06 14:00:02 -0500194 "Failed to transfer data between BMC and remote terminus with file read on upstream '{UPSTREAM}' of length '{LENGTH}' at offset '{OFFSET}' failed, error number - {ERROR_NUM}",
195 "ERROR_NUM", errno, "UPSTREAM", upstream, "LENGTH", length,
196 "OFFSET", offset);
Deepak Kodihalli15211b42019-12-14 02:24:49 -0600197 return rc;
198 }
199 if (rc != static_cast<int>(length))
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530200 {
Riya Dixit49cfb132023-03-02 04:26:53 -0600201 error(
Riya Dixitfc84f632024-04-06 14:00:02 -0500202 "Failed to transfer data between BMC and remote terminus mismatched for number of characters to read on upstream '{UPSTREAM}' and the length '{LENGTH}' read and count '{RC}'",
203 "UPSTREAM", upstream, "LENGTH", length, "RC", rc);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530204 return -1;
205 }
Deepak Kodihalli15211b42019-12-14 02:24:49 -0600206 memcpy(static_cast<char*>(vgaMemPtr.get()), buffer.data(),
207 pageAlignedLength);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530208 }
209
210 AspeedXdmaOp xdmaOp;
211 xdmaOp.upstream = upstream ? 1 : 0;
212 xdmaOp.hostAddr = address;
213 xdmaOp.len = length;
214
215 rc = write(xdmaFd(), &xdmaOp, sizeof(xdmaOp));
216 if (rc < 0)
217 {
218 rc = -errno;
Riya Dixit49cfb132023-03-02 04:26:53 -0600219 error(
Riya Dixitfc84f632024-04-06 14:00:02 -0500220 "Failed to execute the DMA operation on data between BMC and remote terminus for upstream '{UPSTREAM}' of length '{LENGTH}' at address '{ADDRESS}', response code '{RC}'",
221 "RC", rc, "UPSTREAM", upstream, "ADDRESS", address, "LENGTH",
222 length);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530223 return rc;
224 }
225
226 if (!upstream)
227 {
Deepak Kodihalli15211b42019-12-14 02:24:49 -0600228 rc = lseek(fd, offset, SEEK_SET);
229 if (rc == -1)
Sampa Misra854e61f2019-08-22 04:36:47 -0500230 {
Riya Dixit49cfb132023-03-02 04:26:53 -0600231 error(
Riya Dixitfc84f632024-04-06 14:00:02 -0500232 "Failed to transfer data between BMC and remote terminus due to lseek failure '{UPSTREAM}' at offset '{OFFSET}' failed, error number - {ERROR_NUM}",
233 "ERROR_NUM", errno, "UPSTREAM", upstream, "OFFSET", offset);
Deepak Kodihalli15211b42019-12-14 02:24:49 -0600234 return rc;
Sampa Misra854e61f2019-08-22 04:36:47 -0500235 }
Deepak Kodihalli15211b42019-12-14 02:24:49 -0600236 rc = write(fd, static_cast<const char*>(vgaMemPtr.get()), length);
237 if (rc == -1)
238 {
Riya Dixit49cfb132023-03-02 04:26:53 -0600239 error(
Riya Dixitfc84f632024-04-06 14:00:02 -0500240 "Failed to transfer data between BMC and remote terminus where file write upstream '{UPSTREAM}' of length '{LENGTH}' at offset '{OFFSET}' failed, error number - {ERROR_NUM}",
241 "ERROR_NUM", errno, "UPSTREAM", upstream, "LENGTH", length,
242 "OFFSET", offset);
Deepak Kodihalli15211b42019-12-14 02:24:49 -0600243 return rc;
244 }
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530245 }
246
247 return 0;
248}
249
250} // namespace dma
251
Deepak Kodihallibc669f12019-11-28 08:52:07 -0600252namespace oem_ibm
253{
Riya Dixit8394c452024-04-06 12:15:23 -0500254void encodeRWResponseHandler(uint8_t instance_id, uint8_t command,
255 uint8_t completion_code, uint32_t length,
256 struct pldm_msg* msg)
257{
258 int rc = encode_rw_file_memory_resp(instance_id, command, completion_code,
259 length, msg);
260 if (rc != PLDM_SUCCESS)
261 {
262 error(
263 "Failed to encode response for command {COMMAND}, response code '{RC}'",
264 "COMMAND", command, "RC", rc);
265 }
266}
267
268void encodeReadResponseHandler(uint8_t instance_id, uint8_t completion_code,
269 uint32_t length, struct pldm_msg* msg)
270{
271 int rc = encode_read_file_resp(instance_id, completion_code, length, msg);
272 if (rc != PLDM_SUCCESS)
273 {
274 error("Failed to encode read file response, response code '{RC}'", "RC",
275 rc);
276 }
277}
278
279void encodeWriteResponseHandler(uint8_t instance_id, uint8_t completion_code,
280 uint32_t length, struct pldm_msg* msg)
281{
282 int rc = encode_write_file_resp(instance_id, completion_code, length, msg);
283 if (rc != PLDM_SUCCESS)
284 {
285 error("Failed to encode write file response, response code '{RC}'",
286 "RC", rc);
287 }
288}
289
Patrick Williams16c2a0a2024-08-16 15:20:59 -0400290void encodeGetFileResponseHandler(
291 uint8_t instance_id, uint8_t completion_code, uint32_t next_transfer_handle,
292 uint8_t transfer_flag, const uint8_t* table_data, size_t table_size,
293 struct pldm_msg* msg)
Riya Dixit8394c452024-04-06 12:15:23 -0500294{
295 int rc = encode_get_file_table_resp(instance_id, completion_code,
296 next_transfer_handle, transfer_flag,
297 table_data, table_size, msg);
298 if (rc != PLDM_SUCCESS)
299 {
300 error("Failed to encode get file table response, response code '{RC}'",
301 "RC", rc);
302 }
303}
304
305void encodeRWTypeMemoryResponseHandler(uint8_t instance_id, uint8_t command,
306 uint8_t completion_code, uint32_t length,
307 struct pldm_msg* msg)
308{
309 int rc = encode_rw_file_by_type_memory_resp(instance_id, command,
310 completion_code, length, msg);
311 if (rc != PLDM_SUCCESS)
312 {
313 error(
314 "Failed to encode read/write file by type memory response, response code '{RC}'",
315 "RC", rc);
316 }
317}
318
319void encodeRWTypeResponseHandler(uint8_t instance_id, uint8_t command,
320 uint8_t completion_code, uint32_t length,
321 struct pldm_msg* msg)
322{
323 int rc = encode_rw_file_by_type_resp(instance_id, command, completion_code,
324 length, msg);
325 if (rc != PLDM_SUCCESS)
326 {
327 error(
328 "Failed to encode response for command {COMMAND}, response code '{RC}'",
329 "COMMAND", command, "RC", rc);
330 }
331}
332
333void encodeFileAckResponseHandler(uint8_t instance_id, uint8_t completion_code,
334 struct pldm_msg* msg)
335{
336 int rc = encode_file_ack_resp(instance_id, completion_code, msg);
337 if (rc != PLDM_SUCCESS)
338 {
339 error("Failed to encode file ack response, response code '{RC}'", "RC",
340 rc);
341 }
342}
343
Deepak Kodihallibc669f12019-11-28 08:52:07 -0600344Response Handler::readFileIntoMemory(const pldm_msg* request,
345 size_t payloadLength)
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530346{
347 uint32_t fileHandle = 0;
348 uint32_t offset = 0;
349 uint32_t length = 0;
350 uint64_t address = 0;
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530351
352 Response response((sizeof(pldm_msg_hdr) + PLDM_RW_FILE_MEM_RESP_BYTES), 0);
353 auto responsePtr = reinterpret_cast<pldm_msg*>(response.data());
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530354 if (payloadLength != PLDM_RW_FILE_MEM_REQ_BYTES)
355 {
Riya Dixit8394c452024-04-06 12:15:23 -0500356 error(
357 "Failed to read file into memory as payload length '{LENGTH}' not equal to '{REQ_LENGTH}'",
358 "LENGTH", payloadLength, "REQ_LENGTH", PLDM_RW_FILE_MEM_REQ_BYTES);
359 encodeRWResponseHandler(request->hdr.instance_id,
360 PLDM_READ_FILE_INTO_MEMORY,
361 PLDM_ERROR_INVALID_LENGTH, 0, responsePtr);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530362 return response;
363 }
364
Riya Dixit8394c452024-04-06 12:15:23 -0500365 int responseCode = decode_rw_file_memory_req(
366 request, payloadLength, &fileHandle, &offset, &length, &address);
367 if (responseCode != PLDM_SUCCESS)
368 {
369 error(
370 "Failed to decode read file into memory request, response code '{RC}'",
371 "RC", responseCode);
372 }
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530373
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530374 using namespace pldm::filetable;
375 auto& table = buildFileTable(FILE_TABLE_JSON);
376 FileEntry value{};
377
378 try
379 {
380 value = table.at(fileHandle);
381 }
Patrick Williams51330582021-10-06 12:48:56 -0500382 catch (const std::exception& e)
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530383 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500384 error(
385 "File handle '{HANDLE}' does not exist in the file table, error - {ERROR}",
386 "HANDLE", fileHandle, "ERROR", e);
Riya Dixit8394c452024-04-06 12:15:23 -0500387 encodeRWResponseHandler(request->hdr.instance_id,
388 PLDM_READ_FILE_INTO_MEMORY,
389 PLDM_INVALID_FILE_HANDLE, 0, responsePtr);
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530390 return response;
391 }
392
393 if (!fs::exists(value.fsPath))
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530394 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500395 error("File '{PATH}' and handle '{FILE_HANDLE}' with does not exist",
396 "PATH", value.fsPath, "FILE_HANDLE", fileHandle);
Riya Dixit8394c452024-04-06 12:15:23 -0500397 encodeRWResponseHandler(request->hdr.instance_id,
398 PLDM_READ_FILE_INTO_MEMORY,
399 PLDM_INVALID_FILE_HANDLE, 0, responsePtr);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530400 return response;
401 }
402
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530403 auto fileSize = fs::file_size(value.fsPath);
Riya Dixit8394c452024-04-06 12:15:23 -0500404 if (!fileSize)
405 {
406 error(
407 "Failed to PLDM_READ_FILE_INTO_MEMORY from file {PATH} with size '{SIZE}'",
408 "PATH", value.fsPath, "SIZE", fileSize);
409 encodeRWResponseHandler(request->hdr.instance_id,
410 PLDM_READ_FILE_INTO_MEMORY,
411 PLDM_DATA_OUT_OF_RANGE, 0, responsePtr);
412 return response;
413 }
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530414 if (offset >= fileSize)
415 {
Sagar Srinivas82257922023-07-10 08:12:22 -0500416 error(
Riya Dixitfc84f632024-04-06 14:00:02 -0500417 "Offset '{OFFSET}' exceeds file size '{SIZE}' and file handle '{FILE_HANDLE}'",
418 "OFFSET", offset, "SIZE", fileSize, "FILE_HANDLE", fileHandle);
Riya Dixit8394c452024-04-06 12:15:23 -0500419 encodeRWResponseHandler(request->hdr.instance_id,
420 PLDM_READ_FILE_INTO_MEMORY,
421 PLDM_DATA_OUT_OF_RANGE, 0, responsePtr);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530422 return response;
423 }
424
425 if (offset + length > fileSize)
426 {
427 length = fileSize - offset;
428 }
429
Riya Dixit8394c452024-04-06 12:15:23 -0500430 if (!length || length % dma::minSize)
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530431 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500432 error("Packet length '{LENGTH}' is non multiple of minimum DMA size",
433 "LENGTH", length);
Riya Dixit8394c452024-04-06 12:15:23 -0500434 encodeRWResponseHandler(request->hdr.instance_id,
435 PLDM_READ_FILE_INTO_MEMORY,
436 PLDM_ERROR_INVALID_LENGTH, 0, responsePtr);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530437 return response;
438 }
439
440 using namespace dma;
441 DMA intf;
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530442 return transferAll<DMA>(&intf, PLDM_READ_FILE_INTO_MEMORY, value.fsPath,
Jinu Joy Thomas33705fd2019-07-02 16:03:05 +0530443 offset, length, address, true,
444 request->hdr.instance_id);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530445}
446
Deepak Kodihallibc669f12019-11-28 08:52:07 -0600447Response Handler::writeFileFromMemory(const pldm_msg* request,
448 size_t payloadLength)
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530449{
450 uint32_t fileHandle = 0;
451 uint32_t offset = 0;
452 uint32_t length = 0;
453 uint64_t address = 0;
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530454
455 Response response(sizeof(pldm_msg_hdr) + PLDM_RW_FILE_MEM_RESP_BYTES, 0);
456 auto responsePtr = reinterpret_cast<pldm_msg*>(response.data());
457
458 if (payloadLength != PLDM_RW_FILE_MEM_REQ_BYTES)
459 {
Riya Dixit8394c452024-04-06 12:15:23 -0500460 error(
461 "Failed to write file from memory as payload length '{LENGTH}' not equal to '{REQ_LENGTH}'",
462 "LENGTH", payloadLength, "REQ_LENGTH", PLDM_RW_FILE_MEM_REQ_BYTES);
463 encodeRWResponseHandler(request->hdr.instance_id,
464 PLDM_WRITE_FILE_FROM_MEMORY,
465 PLDM_ERROR_INVALID_LENGTH, 0, responsePtr);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530466 return response;
467 }
468
Riya Dixit8394c452024-04-06 12:15:23 -0500469 int responseCode = decode_rw_file_memory_req(
470 request, payloadLength, &fileHandle, &offset, &length, &address);
471 if (responseCode != PLDM_SUCCESS)
472 {
473 error(
474 "Failed to decode write file from memory request, response code '{RC}'",
475 "RC", responseCode);
476 }
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530477
Riya Dixit8394c452024-04-06 12:15:23 -0500478 if (!length || length % dma::minSize)
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530479 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500480 error("Packet length '{LENGTH}' is non multiple of minimum DMA size",
481 "LENGTH", length);
Riya Dixit8394c452024-04-06 12:15:23 -0500482 encodeRWResponseHandler(request->hdr.instance_id,
483 PLDM_WRITE_FILE_FROM_MEMORY,
484 PLDM_ERROR_INVALID_LENGTH, 0, responsePtr);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530485 return response;
486 }
487
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530488 using namespace pldm::filetable;
489 auto& table = buildFileTable(FILE_TABLE_JSON);
490 FileEntry value{};
491
492 try
493 {
494 value = table.at(fileHandle);
495 }
Patrick Williams51330582021-10-06 12:48:56 -0500496 catch (const std::exception& e)
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530497 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500498 error(
499 "File handle '{HANDLE}' does not exist in the file table, error - {ERROR}",
500 "HANDLE", fileHandle, "ERROR", e);
Riya Dixit8394c452024-04-06 12:15:23 -0500501 encodeRWResponseHandler(request->hdr.instance_id,
502 PLDM_WRITE_FILE_FROM_MEMORY,
503 PLDM_INVALID_FILE_HANDLE, 0, responsePtr);
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530504 return response;
505 }
506
507 if (!fs::exists(value.fsPath))
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530508 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500509 error("File '{PATH}' does not exist for file handle '{FILE_HANDLE}'",
510 "PATH", value.fsPath, "FILE_HANDLE", fileHandle);
Riya Dixit8394c452024-04-06 12:15:23 -0500511 encodeRWResponseHandler(request->hdr.instance_id,
512 PLDM_WRITE_FILE_FROM_MEMORY,
513 PLDM_INVALID_FILE_HANDLE, 0, responsePtr);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530514 return response;
515 }
516
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530517 auto fileSize = fs::file_size(value.fsPath);
Riya Dixit8394c452024-04-06 12:15:23 -0500518 if (!fileSize)
519 {
520 info(
521 "File '{PATH}' has size '{SIZE}' for command PLDM_WRITE_FILE_FROM_MEMORY",
522 "PATH", value.fsPath, "SIZE", fileSize);
523 }
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530524 if (offset >= fileSize)
525 {
Sagar Srinivas82257922023-07-10 08:12:22 -0500526 error(
Riya Dixitfc84f632024-04-06 14:00:02 -0500527 "Offset '{OFFSET}' exceeds file size {SIZE} for file '{PATH} and handle {FILE_HANDLE}",
528 "OFFSET", offset, "SIZE", fileSize, "PATH", value.fsPath,
529 "FILE_HANDLE", fileHandle);
Riya Dixit8394c452024-04-06 12:15:23 -0500530 encodeRWResponseHandler(request->hdr.instance_id,
531 PLDM_WRITE_FILE_FROM_MEMORY,
532 PLDM_DATA_OUT_OF_RANGE, 0, responsePtr);
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530533 return response;
534 }
535
536 using namespace dma;
537 DMA intf;
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530538 return transferAll<DMA>(&intf, PLDM_WRITE_FILE_FROM_MEMORY, value.fsPath,
Jinu Joy Thomas33705fd2019-07-02 16:03:05 +0530539 offset, length, address, false,
540 request->hdr.instance_id);
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530541}
542
Deepak Kodihallibc669f12019-11-28 08:52:07 -0600543Response Handler::getFileTable(const pldm_msg* request, size_t payloadLength)
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530544{
545 uint32_t transferHandle = 0;
546 uint8_t transferFlag = 0;
547 uint8_t tableType = 0;
548
Patrick Williams16c2a0a2024-08-16 15:20:59 -0400549 Response response(
550 sizeof(pldm_msg_hdr) + PLDM_GET_FILE_TABLE_MIN_RESP_BYTES);
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530551 auto responsePtr = reinterpret_cast<pldm_msg*>(response.data());
552
553 if (payloadLength != PLDM_GET_FILE_TABLE_REQ_BYTES)
554 {
Riya Dixit8394c452024-04-06 12:15:23 -0500555 error(
556 "Failed to get file table as payload length '{LENGTH}' not equal to required length '{REQ_LENGTH}'",
557 "LENGTH", payloadLength, "REQ_LENGTH",
558 PLDM_GET_FILE_TABLE_REQ_BYTES);
559 encodeGetFileResponseHandler(request->hdr.instance_id,
560 PLDM_ERROR_INVALID_LENGTH, 0, 0, nullptr,
561 0, responsePtr);
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530562 return response;
563 }
564
Zahed Hossain223a73d2019-07-04 12:46:18 -0500565 auto rc = decode_get_file_table_req(request, payloadLength, &transferHandle,
566 &transferFlag, &tableType);
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530567 if (rc)
568 {
Riya Dixit8394c452024-04-06 12:15:23 -0500569 error("Failed to decode get file table request, response code '{RC}'",
570 "RC", rc);
571 encodeGetFileResponseHandler(request->hdr.instance_id, rc, 0, 0,
572 nullptr, 0, responsePtr);
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530573 return response;
574 }
575
576 if (tableType != PLDM_FILE_ATTRIBUTE_TABLE)
577 {
Riya Dixit8394c452024-04-06 12:15:23 -0500578 error(
579 "Failed to match table type '{TYPE}' with expected table type '{REQ_TYPE}'",
580 "TYPE", tableType, "REQ_TYPE", PLDM_FILE_ATTRIBUTE_TABLE);
581 encodeGetFileResponseHandler(request->hdr.instance_id,
582 PLDM_INVALID_FILE_TABLE_TYPE, 0, 0,
583 nullptr, 0, responsePtr);
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530584 return response;
585 }
586
587 using namespace pldm::filetable;
588 auto table = buildFileTable(FILE_TABLE_JSON);
589 auto attrTable = table();
590 response.resize(response.size() + attrTable.size());
591 responsePtr = reinterpret_cast<pldm_msg*>(response.data());
592
593 if (attrTable.empty())
594 {
Riya Dixit8394c452024-04-06 12:15:23 -0500595 error("PLDM file attribute table is empty");
596 encodeGetFileResponseHandler(request->hdr.instance_id,
597 PLDM_FILE_TABLE_UNAVAILABLE, 0, 0, nullptr,
598 0, responsePtr);
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530599 return response;
600 }
601
Riya Dixit8394c452024-04-06 12:15:23 -0500602 encodeGetFileResponseHandler(request->hdr.instance_id, PLDM_SUCCESS, 0,
603 PLDM_START_AND_END, attrTable.data(),
604 attrTable.size(), responsePtr);
Tom Joseph0c6d22c2019-06-26 09:58:41 +0530605 return response;
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +0530606}
607
Deepak Kodihallibc669f12019-11-28 08:52:07 -0600608Response Handler::readFile(const pldm_msg* request, size_t payloadLength)
vkaverap5b914c32019-06-30 22:23:54 -0500609{
610 uint32_t fileHandle = 0;
611 uint32_t offset = 0;
612 uint32_t length = 0;
613
614 Response response(sizeof(pldm_msg_hdr) + PLDM_READ_FILE_RESP_BYTES);
615 auto responsePtr = reinterpret_cast<pldm_msg*>(response.data());
616
617 if (payloadLength != PLDM_READ_FILE_REQ_BYTES)
618 {
Riya Dixit8394c452024-04-06 12:15:23 -0500619 error(
620 "Failed to read file as payload length '{LENGTH}' not equal to '{REQ_LENGTH}'",
621 "LENGTH", payloadLength, "REQ_LENGTH", PLDM_READ_FILE_REQ_BYTES);
622 encodeReadResponseHandler(request->hdr.instance_id,
623 PLDM_ERROR_INVALID_LENGTH, length,
624 responsePtr);
vkaverap5b914c32019-06-30 22:23:54 -0500625 return response;
626 }
627
628 auto rc = decode_read_file_req(request, payloadLength, &fileHandle, &offset,
629 &length);
630
631 if (rc)
632 {
Riya Dixit8394c452024-04-06 12:15:23 -0500633 error("Failed to decode read file request, response code '{RC}'", "RC",
634 rc);
635 encodeReadResponseHandler(request->hdr.instance_id, rc, 0, responsePtr);
vkaverap5b914c32019-06-30 22:23:54 -0500636 return response;
637 }
638
639 using namespace pldm::filetable;
640 auto& table = buildFileTable(FILE_TABLE_JSON);
641 FileEntry value{};
642
643 try
644 {
645 value = table.at(fileHandle);
646 }
Patrick Williams51330582021-10-06 12:48:56 -0500647 catch (const std::exception& e)
vkaverap5b914c32019-06-30 22:23:54 -0500648 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500649 error(
650 "File handle '{HANDLE}' does not exist in the file table, error - {ERROR}",
651 "HANDLE", fileHandle, "ERROR", e);
Kamalkumar Patel58cbcaf2023-10-06 03:48:25 -0500652
Riya Dixit8394c452024-04-06 12:15:23 -0500653 encodeReadResponseHandler(request->hdr.instance_id,
654 PLDM_INVALID_FILE_HANDLE, length,
655 responsePtr);
vkaverap5b914c32019-06-30 22:23:54 -0500656 return response;
657 }
658
659 if (!fs::exists(value.fsPath))
660 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500661 error("File '{PATH}' and handle {FILE_HANDLE} does not exist", "PATH",
662 value.fsPath, "FILE_HANDLE", fileHandle);
Riya Dixit8394c452024-04-06 12:15:23 -0500663 encodeReadResponseHandler(request->hdr.instance_id,
664 PLDM_INVALID_FILE_HANDLE, length,
665 responsePtr);
vkaverap5b914c32019-06-30 22:23:54 -0500666 return response;
667 }
668
669 auto fileSize = fs::file_size(value.fsPath);
Riya Dixit8394c452024-04-06 12:15:23 -0500670 if (!fileSize)
671 {
672 error("Failed to read file {PATH} with size '{SIZE}'", "PATH",
673 value.fsPath, "SIZE", fileSize);
674 encodeRWResponseHandler(request->hdr.instance_id,
675 PLDM_READ_FILE_INTO_MEMORY,
676 PLDM_DATA_OUT_OF_RANGE, 0, responsePtr);
677 return response;
678 }
679
vkaverap5b914c32019-06-30 22:23:54 -0500680 if (offset >= fileSize)
681 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500682 error(
683 "Offset '{OFFSET}' exceeds file size '{SIZE}' for file '{PATH}' and file handle '{HANDLE}'",
684 "OFFSET", offset, "SIZE", fileSize, "PATH", value.fsPath, "HANDLE",
685 fileHandle);
Riya Dixit8394c452024-04-06 12:15:23 -0500686 encodeReadResponseHandler(request->hdr.instance_id,
687 PLDM_DATA_OUT_OF_RANGE, length, responsePtr);
vkaverap5b914c32019-06-30 22:23:54 -0500688 return response;
689 }
690
691 if (offset + length > fileSize)
692 {
693 length = fileSize - offset;
694 }
695
696 response.resize(response.size() + length);
697 responsePtr = reinterpret_cast<pldm_msg*>(response.data());
698 auto fileDataPos = reinterpret_cast<char*>(responsePtr);
699 fileDataPos += sizeof(pldm_msg_hdr) + sizeof(uint8_t) + sizeof(length);
700
701 std::ifstream stream(value.fsPath, std::ios::in | std::ios::binary);
702 stream.seekg(offset);
703 stream.read(fileDataPos, length);
704
Riya Dixit8394c452024-04-06 12:15:23 -0500705 encodeReadResponseHandler(request->hdr.instance_id, PLDM_SUCCESS, length,
706 responsePtr);
vkaverap5b914c32019-06-30 22:23:54 -0500707
708 return response;
709}
710
Deepak Kodihallibc669f12019-11-28 08:52:07 -0600711Response Handler::writeFile(const pldm_msg* request, size_t payloadLength)
vkaverap5b914c32019-06-30 22:23:54 -0500712{
713 uint32_t fileHandle = 0;
714 uint32_t offset = 0;
715 uint32_t length = 0;
716 size_t fileDataOffset = 0;
717
718 Response response(sizeof(pldm_msg_hdr) + PLDM_WRITE_FILE_RESP_BYTES);
719 auto responsePtr = reinterpret_cast<pldm_msg*>(response.data());
720
721 if (payloadLength < PLDM_WRITE_FILE_REQ_BYTES)
722 {
Riya Dixit8394c452024-04-06 12:15:23 -0500723 error(
724 "Failed to write file as payload length '{LENGTH}' less than '{REQ_LENGTH}'",
725 "LENGTH", payloadLength, "REQ_LENGTH", PLDM_WRITE_FILE_REQ_BYTES);
726 encodeWriteResponseHandler(request->hdr.instance_id,
727 PLDM_ERROR_INVALID_LENGTH, 0, responsePtr);
vkaverap5b914c32019-06-30 22:23:54 -0500728 return response;
729 }
730
731 auto rc = decode_write_file_req(request, payloadLength, &fileHandle,
732 &offset, &length, &fileDataOffset);
733
734 if (rc)
735 {
Riya Dixit8394c452024-04-06 12:15:23 -0500736 error("Failed to decode write file request, response code '{RC}'", "RC",
737 rc);
738 encodeWriteResponseHandler(request->hdr.instance_id, rc, 0,
739 responsePtr);
vkaverap5b914c32019-06-30 22:23:54 -0500740 return response;
741 }
742
743 using namespace pldm::filetable;
744 auto& table = buildFileTable(FILE_TABLE_JSON);
745 FileEntry value{};
746
747 try
748 {
749 value = table.at(fileHandle);
750 }
Patrick Williams51330582021-10-06 12:48:56 -0500751 catch (const std::exception& e)
vkaverap5b914c32019-06-30 22:23:54 -0500752 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500753 error(
754 "File handle '{HANDLE}' does not exist in the file table, error - {ERROR}",
755 "HANDLE", fileHandle, "ERROR", e);
Riya Dixit8394c452024-04-06 12:15:23 -0500756 encodeWriteResponseHandler(request->hdr.instance_id,
757 PLDM_INVALID_FILE_HANDLE, 0, responsePtr);
vkaverap5b914c32019-06-30 22:23:54 -0500758 return response;
759 }
760
761 if (!fs::exists(value.fsPath))
762 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500763 error("File '{PATH}' and handle {FILE_HANDLE} does not exist", "PATH",
764 value.fsPath, "FILE_HANDLE", fileHandle);
Riya Dixit8394c452024-04-06 12:15:23 -0500765 encodeWriteResponseHandler(request->hdr.instance_id,
766 PLDM_INVALID_FILE_HANDLE, 0, responsePtr);
vkaverap5b914c32019-06-30 22:23:54 -0500767 return response;
768 }
769
770 auto fileSize = fs::file_size(value.fsPath);
Riya Dixit8394c452024-04-06 12:15:23 -0500771
772 if (!fileSize)
773 {
774 info("File {PATH} has size '{SIZE}' for write file command", "PATH",
775 value.fsPath, "SIZE", fileSize);
776 }
777
vkaverap5b914c32019-06-30 22:23:54 -0500778 if (offset >= fileSize)
779 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500780 error(
781 "Offset '{OFFSET}' exceeds file size '{SIZE}' for file '{PATH}' and handle {FILE_HANDLE}",
782 "OFFSET", offset, "SIZE", fileSize, "PATH", value.fsPath,
783 "FILE_HANDLE", fileHandle);
Riya Dixit8394c452024-04-06 12:15:23 -0500784 encodeWriteResponseHandler(request->hdr.instance_id,
785 PLDM_DATA_OUT_OF_RANGE, 0, responsePtr);
vkaverap5b914c32019-06-30 22:23:54 -0500786 return response;
787 }
788
Patrick Williams16c2a0a2024-08-16 15:20:59 -0400789 auto fileDataPos =
790 reinterpret_cast<const char*>(request->payload) + fileDataOffset;
vkaverap5b914c32019-06-30 22:23:54 -0500791
792 std::ofstream stream(value.fsPath,
793 std::ios::in | std::ios::out | std::ios::binary);
794 stream.seekp(offset);
795 stream.write(fileDataPos, length);
796
Riya Dixit8394c452024-04-06 12:15:23 -0500797 encodeWriteResponseHandler(request->hdr.instance_id, PLDM_SUCCESS, length,
798 responsePtr);
vkaverap5b914c32019-06-30 22:23:54 -0500799
800 return response;
801}
802
Deepak Kodihallif6d3a832019-11-19 07:00:29 -0600803Response rwFileByTypeIntoMemory(uint8_t cmd, const pldm_msg* request,
Sampa Misra69508502020-09-08 00:08:21 -0500804 size_t payloadLength,
805 oem_platform::Handler* oemPlatformHandler)
Sampa Misra854e61f2019-08-22 04:36:47 -0500806{
807 Response response(
808 sizeof(pldm_msg_hdr) + PLDM_RW_FILE_BY_TYPE_MEM_RESP_BYTES, 0);
809 auto responsePtr = reinterpret_cast<pldm_msg*>(response.data());
810
811 if (payloadLength != PLDM_RW_FILE_BY_TYPE_MEM_REQ_BYTES)
812 {
Riya Dixit8394c452024-04-06 12:15:23 -0500813 error(
814 "Failed to read file into memory as payload length '{LENGTH}' not equal to '{REQ_LENGTH}'",
815 "LENGTH", payloadLength, "REQ_LENGTH",
816 PLDM_RW_FILE_BY_TYPE_MEM_REQ_BYTES);
817 encodeRWTypeMemoryResponseHandler(request->hdr.instance_id, cmd,
818 PLDM_ERROR_INVALID_LENGTH, 0,
819 responsePtr);
Sampa Misra854e61f2019-08-22 04:36:47 -0500820 return response;
821 }
822
823 uint16_t fileType{};
824 uint32_t fileHandle{};
825 uint32_t offset{};
826 uint32_t length{};
827 uint64_t address{};
Patrick Williams16c2a0a2024-08-16 15:20:59 -0400828 auto rc = decode_rw_file_by_type_memory_req(
829 request, payloadLength, &fileType, &fileHandle, &offset, &length,
830 &address);
Sampa Misra854e61f2019-08-22 04:36:47 -0500831 if (rc != PLDM_SUCCESS)
832 {
Riya Dixit8394c452024-04-06 12:15:23 -0500833 error(
834 "Failed to decode read/write file by type memory request, response code '{RC}'",
835 "RC", rc);
836 encodeRWTypeMemoryResponseHandler(request->hdr.instance_id, cmd, rc, 0,
837 responsePtr);
Sampa Misra854e61f2019-08-22 04:36:47 -0500838 return response;
839 }
Riya Dixit8394c452024-04-06 12:15:23 -0500840 if (!length || length % dma::minSize)
Sampa Misra854e61f2019-08-22 04:36:47 -0500841 {
Riya Dixit8394c452024-04-06 12:15:23 -0500842 error(
843 "Packet length '{LENGTH}' is non multiple of minimum DMA size for command {CMD}",
844 "LENGTH", length, "CMD", cmd);
845 encodeRWTypeMemoryResponseHandler(request->hdr.instance_id, cmd,
846 PLDM_ERROR_INVALID_LENGTH, 0,
847 responsePtr);
Sampa Misra854e61f2019-08-22 04:36:47 -0500848 return response;
849 }
850
851 std::unique_ptr<FileHandler> handler{};
852 try
853 {
854 handler = getHandlerByType(fileType, fileHandle);
855 }
856 catch (const InternalFailure& e)
857 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500858 error("Unknown file type '{TYPE}', error - {ERROR} ", "TYPE", fileType,
859 "ERROR", e);
Riya Dixit8394c452024-04-06 12:15:23 -0500860 encodeRWTypeMemoryResponseHandler(request->hdr.instance_id, cmd,
861 PLDM_INVALID_FILE_TYPE, 0,
862 responsePtr);
Sampa Misra854e61f2019-08-22 04:36:47 -0500863 return response;
864 }
865
Deepak Kodihallif6d3a832019-11-19 07:00:29 -0600866 rc = cmd == PLDM_WRITE_FILE_BY_TYPE_FROM_MEMORY
Sampa Misra69508502020-09-08 00:08:21 -0500867 ? handler->writeFromMemory(offset, length, address,
868 oemPlatformHandler)
869 : handler->readIntoMemory(offset, length, address,
870 oemPlatformHandler);
Riya Dixit8394c452024-04-06 12:15:23 -0500871 encodeRWTypeMemoryResponseHandler(request->hdr.instance_id, cmd, rc, length,
872 responsePtr);
Sampa Misra854e61f2019-08-22 04:36:47 -0500873 return response;
874}
875
Deepak Kodihallibc669f12019-11-28 08:52:07 -0600876Response Handler::writeFileByTypeFromMemory(const pldm_msg* request,
877 size_t payloadLength)
Deepak Kodihallif6d3a832019-11-19 07:00:29 -0600878{
879 return rwFileByTypeIntoMemory(PLDM_WRITE_FILE_BY_TYPE_FROM_MEMORY, request,
Sampa Misra69508502020-09-08 00:08:21 -0500880 payloadLength, oemPlatformHandler);
Deepak Kodihallif6d3a832019-11-19 07:00:29 -0600881}
882
Deepak Kodihallibc669f12019-11-28 08:52:07 -0600883Response Handler::readFileByTypeIntoMemory(const pldm_msg* request,
884 size_t payloadLength)
Deepak Kodihallif6d3a832019-11-19 07:00:29 -0600885{
886 return rwFileByTypeIntoMemory(PLDM_READ_FILE_BY_TYPE_INTO_MEMORY, request,
Sampa Misra69508502020-09-08 00:08:21 -0500887 payloadLength, oemPlatformHandler);
Deepak Kodihallif6d3a832019-11-19 07:00:29 -0600888}
889
Sampa Misra18967162020-01-14 02:31:41 -0600890Response Handler::writeFileByType(const pldm_msg* request, size_t payloadLength)
891{
892 Response response(sizeof(pldm_msg_hdr) + PLDM_RW_FILE_BY_TYPE_RESP_BYTES);
893 auto responsePtr = reinterpret_cast<pldm_msg*>(response.data());
894
Sampa Misrad823cc02020-03-24 04:53:20 -0500895 if (payloadLength < PLDM_RW_FILE_BY_TYPE_REQ_BYTES)
Sampa Misra18967162020-01-14 02:31:41 -0600896 {
Riya Dixit8394c452024-04-06 12:15:23 -0500897 error(
898 "Failed to write file by type as payload length '{LENGTH}' less than '{REQ_LENGTH}'",
899 "LENGTH", payloadLength, "REQ_LENGTH",
900 PLDM_RW_FILE_BY_TYPE_REQ_BYTES);
901 encodeRWTypeResponseHandler(request->hdr.instance_id,
Sampa Misra18967162020-01-14 02:31:41 -0600902 PLDM_WRITE_FILE_BY_TYPE,
903 PLDM_ERROR_INVALID_LENGTH, 0, responsePtr);
904 return response;
905 }
906 uint16_t fileType{};
907 uint32_t fileHandle{};
908 uint32_t offset{};
909 uint32_t length{};
910
911 auto rc = decode_rw_file_by_type_req(request, payloadLength, &fileType,
912 &fileHandle, &offset, &length);
913 if (rc != PLDM_SUCCESS)
914 {
Riya Dixit8394c452024-04-06 12:15:23 -0500915 error("Failed decoded write file by type request, response code '{RC}'",
916 "RC", rc);
917 encodeRWTypeResponseHandler(request->hdr.instance_id,
Sampa Misra18967162020-01-14 02:31:41 -0600918 PLDM_WRITE_FILE_BY_TYPE, rc, 0,
919 responsePtr);
920 return response;
921 }
922
923 std::unique_ptr<FileHandler> handler{};
924 try
925 {
926 handler = getHandlerByType(fileType, fileHandle);
927 }
928 catch (const InternalFailure& e)
929 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500930 error("Unknown file type '{TYPE}', error - {ERROR}", "TYPE", fileType,
Kamalkumar Patel58cbcaf2023-10-06 03:48:25 -0500931 "ERROR", e);
Riya Dixit8394c452024-04-06 12:15:23 -0500932 encodeRWTypeResponseHandler(request->hdr.instance_id,
Sampa Misra18967162020-01-14 02:31:41 -0600933 PLDM_WRITE_FILE_BY_TYPE,
934 PLDM_INVALID_FILE_TYPE, 0, responsePtr);
935 return response;
936 }
937
938 rc = handler->write(reinterpret_cast<const char*>(
Sampa Misrad823cc02020-03-24 04:53:20 -0500939 request->payload + PLDM_RW_FILE_BY_TYPE_REQ_BYTES),
Sampa Misra69508502020-09-08 00:08:21 -0500940 offset, length, oemPlatformHandler);
Riya Dixit8394c452024-04-06 12:15:23 -0500941 encodeRWTypeResponseHandler(request->hdr.instance_id,
Sampa Misra18967162020-01-14 02:31:41 -0600942 PLDM_WRITE_FILE_BY_TYPE, rc, length,
943 responsePtr);
944 return response;
945}
946
Deepak Kodihallibc669f12019-11-28 08:52:07 -0600947Response Handler::readFileByType(const pldm_msg* request, size_t payloadLength)
Deepak Kodihalli75e02f82019-11-20 02:51:05 -0600948{
949 Response response(sizeof(pldm_msg_hdr) + PLDM_RW_FILE_BY_TYPE_RESP_BYTES);
950 auto responsePtr = reinterpret_cast<pldm_msg*>(response.data());
951
952 if (payloadLength != PLDM_RW_FILE_BY_TYPE_REQ_BYTES)
953 {
Riya Dixit8394c452024-04-06 12:15:23 -0500954 error(
955 "Failed to read file by type as payload length '{LENGTH}' less than '{REQ_LENGTH}'",
956 "LENGTH", payloadLength, "REQ_LENGTH",
957 PLDM_RW_FILE_BY_TYPE_REQ_BYTES);
958 encodeRWTypeResponseHandler(request->hdr.instance_id,
Deepak Kodihalli75e02f82019-11-20 02:51:05 -0600959 PLDM_READ_FILE_BY_TYPE,
960 PLDM_ERROR_INVALID_LENGTH, 0, responsePtr);
961 return response;
962 }
963 uint16_t fileType{};
964 uint32_t fileHandle{};
965 uint32_t offset{};
966 uint32_t length{};
967
968 auto rc = decode_rw_file_by_type_req(request, payloadLength, &fileType,
969 &fileHandle, &offset, &length);
970 if (rc != PLDM_SUCCESS)
971 {
Riya Dixit8394c452024-04-06 12:15:23 -0500972 error(
973 "Failed to decode read file by type request, response code '{RC}'",
974 "RC", rc);
975 encodeRWTypeResponseHandler(request->hdr.instance_id,
Deepak Kodihalli75e02f82019-11-20 02:51:05 -0600976 PLDM_READ_FILE_BY_TYPE, rc, 0, responsePtr);
977 return response;
978 }
979
980 std::unique_ptr<FileHandler> handler{};
981 try
982 {
983 handler = getHandlerByType(fileType, fileHandle);
984 }
985 catch (const InternalFailure& e)
986 {
Riya Dixitfc84f632024-04-06 14:00:02 -0500987 error("Unknown file type '{TYPE}', error - {ERROR}", "TYPE", fileType,
Kamalkumar Patel58cbcaf2023-10-06 03:48:25 -0500988 "ERROR", e);
Riya Dixit8394c452024-04-06 12:15:23 -0500989 encodeRWTypeResponseHandler(request->hdr.instance_id,
Deepak Kodihalli75e02f82019-11-20 02:51:05 -0600990 PLDM_READ_FILE_BY_TYPE,
991 PLDM_INVALID_FILE_TYPE, 0, responsePtr);
992 return response;
993 }
994
Sampa Misra69508502020-09-08 00:08:21 -0500995 rc = handler->read(offset, length, response, oemPlatformHandler);
Deepak Kodihalli9a26f892019-12-10 06:48:06 -0600996 responsePtr = reinterpret_cast<pldm_msg*>(response.data());
Riya Dixit8394c452024-04-06 12:15:23 -0500997 encodeRWTypeResponseHandler(request->hdr.instance_id,
Deepak Kodihalli75e02f82019-11-20 02:51:05 -0600998 PLDM_READ_FILE_BY_TYPE, rc, length,
999 responsePtr);
1000 return response;
1001}
1002
Deepak Kodihalli2da1bfe2019-12-14 08:28:09 -06001003Response Handler::fileAck(const pldm_msg* request, size_t payloadLength)
1004{
1005 Response response(sizeof(pldm_msg_hdr) + PLDM_FILE_ACK_RESP_BYTES);
1006 auto responsePtr = reinterpret_cast<pldm_msg*>(response.data());
1007
1008 if (payloadLength != PLDM_FILE_ACK_REQ_BYTES)
1009 {
Riya Dixit8394c452024-04-06 12:15:23 -05001010 error(
1011 "Failed to do file ack as payload length '{LENGTH}' is less than '{REQ_LENGTH}'",
1012 "LENGTH", payloadLength, "REQ_LENGTH", PLDM_FILE_ACK_REQ_BYTES);
1013 encodeFileAckResponseHandler(request->hdr.instance_id,
1014 PLDM_ERROR_INVALID_LENGTH, responsePtr);
Deepak Kodihalli2da1bfe2019-12-14 08:28:09 -06001015 return response;
1016 }
1017 uint16_t fileType{};
1018 uint32_t fileHandle{};
1019 uint8_t fileStatus{};
1020
1021 auto rc = decode_file_ack_req(request, payloadLength, &fileType,
1022 &fileHandle, &fileStatus);
1023 if (rc != PLDM_SUCCESS)
1024 {
Riya Dixit8394c452024-04-06 12:15:23 -05001025 encodeFileAckResponseHandler(request->hdr.instance_id, rc, responsePtr);
Deepak Kodihalli2da1bfe2019-12-14 08:28:09 -06001026 return response;
1027 }
1028
1029 std::unique_ptr<FileHandler> handler{};
1030 try
1031 {
1032 handler = getHandlerByType(fileType, fileHandle);
1033 }
Sampa Misra18967162020-01-14 02:31:41 -06001034
Deepak Kodihalli2da1bfe2019-12-14 08:28:09 -06001035 catch (const InternalFailure& e)
1036 {
Riya Dixitfc84f632024-04-06 14:00:02 -05001037 error("Unknown file type '{TYPE}', error - {ERROR}", "TYPE", fileType,
Kamalkumar Patel58cbcaf2023-10-06 03:48:25 -05001038 "ERROR", e);
Riya Dixit8394c452024-04-06 12:15:23 -05001039 encodeFileAckResponseHandler(request->hdr.instance_id,
1040 PLDM_INVALID_FILE_TYPE, responsePtr);
Deepak Kodihalli2da1bfe2019-12-14 08:28:09 -06001041 return response;
1042 }
1043
1044 rc = handler->fileAck(fileStatus);
Riya Dixit8394c452024-04-06 12:15:23 -05001045 encodeFileAckResponseHandler(request->hdr.instance_id, rc, responsePtr);
Deepak Kodihalli2da1bfe2019-12-14 08:28:09 -06001046 return response;
1047}
1048
George Liu89aad712020-03-12 13:34:51 +08001049Response Handler::getAlertStatus(const pldm_msg* request, size_t payloadLength)
1050{
1051 Response response(sizeof(pldm_msg_hdr) + PLDM_GET_ALERT_STATUS_RESP_BYTES);
1052 auto responsePtr = reinterpret_cast<pldm_msg*>(response.data());
1053 if (payloadLength != PLDM_GET_ALERT_STATUS_REQ_BYTES)
1054 {
Riya Dixit8394c452024-04-06 12:15:23 -05001055 error(
1056 "Failed to get alert status as payload length '{LENGTH}' is less than '{REQ_LENGTH}'",
1057 "LENGTH", payloadLength, "REQ_LENGTH",
1058 PLDM_GET_ALERT_STATUS_REQ_BYTES);
George Liu89aad712020-03-12 13:34:51 +08001059 return CmdHandler::ccOnlyResponse(request, PLDM_ERROR_INVALID_LENGTH);
1060 }
1061
1062 uint8_t versionId{};
1063
1064 auto rc = decode_get_alert_status_req(request, payloadLength, &versionId);
1065 if (rc != PLDM_SUCCESS)
1066 {
Riya Dixit8394c452024-04-06 12:15:23 -05001067 error("Failed to decode get alert status request, response code '{RC}'",
1068 "RC", rc);
George Liu89aad712020-03-12 13:34:51 +08001069 return CmdHandler::ccOnlyResponse(request, rc);
1070 }
1071
1072 if (versionId != 0)
1073 {
Riya Dixit8394c452024-04-06 12:15:23 -05001074 error(
1075 "Failed to get alert status due to unsupported version ID '{VERSION}'",
1076 "VERSION", versionId);
George Liu89aad712020-03-12 13:34:51 +08001077 return CmdHandler::ccOnlyResponse(request,
1078 PLDM_HOST_UNSUPPORTED_FORMAT_VERSION);
1079 }
1080
1081 constexpr uint32_t rackEntry = 0xFF000030;
1082 constexpr uint32_t priCecNode = 0x00008030;
1083 rc = encode_get_alert_status_resp(request->hdr.instance_id, PLDM_SUCCESS,
1084 rackEntry, priCecNode, responsePtr,
1085 PLDM_GET_ALERT_STATUS_RESP_BYTES);
1086 if (rc != PLDM_SUCCESS)
1087 {
Riya Dixit8394c452024-04-06 12:15:23 -05001088 error(
1089 "Failed to encode get alert status response, response code '{RC}'",
1090 "RC", rc);
George Liu89aad712020-03-12 13:34:51 +08001091 return CmdHandler::ccOnlyResponse(request, rc);
1092 }
1093
1094 return response;
1095}
1096
Sampa Misra18967162020-01-14 02:31:41 -06001097Response Handler::newFileAvailable(const pldm_msg* request,
1098 size_t payloadLength)
1099{
1100 Response response(sizeof(pldm_msg_hdr) + PLDM_NEW_FILE_RESP_BYTES);
1101
1102 if (payloadLength != PLDM_NEW_FILE_REQ_BYTES)
1103 {
Riya Dixit8394c452024-04-06 12:15:23 -05001104 error(
1105 "Failed new file available as payload length '{LENGTH}' is less than '{REQ_LENGTH}'",
1106 "LENGTH", payloadLength, "REQ_LENGTH", PLDM_NEW_FILE_REQ_BYTES);
Sampa Misra18967162020-01-14 02:31:41 -06001107 return CmdHandler::ccOnlyResponse(request, PLDM_ERROR_INVALID_LENGTH);
1108 }
1109 uint16_t fileType{};
1110 uint32_t fileHandle{};
1111 uint64_t length{};
1112
1113 auto rc = decode_new_file_req(request, payloadLength, &fileType,
1114 &fileHandle, &length);
1115
1116 if (rc != PLDM_SUCCESS)
1117 {
Riya Dixit8394c452024-04-06 12:15:23 -05001118 error("Failed to decode new file request, response code '{RC}'", "RC",
1119 rc);
Sampa Misra18967162020-01-14 02:31:41 -06001120 return CmdHandler::ccOnlyResponse(request, rc);
1121 }
1122
1123 std::unique_ptr<FileHandler> handler{};
1124 try
1125 {
1126 handler = getHandlerByType(fileType, fileHandle);
1127 }
1128 catch (const InternalFailure& e)
1129 {
Riya Dixitfc84f632024-04-06 14:00:02 -05001130 error("Unknown file type '{TYPE}', error - {ERROR}", "TYPE", fileType,
Kamalkumar Patel58cbcaf2023-10-06 03:48:25 -05001131 "ERROR", e);
Sampa Misra18967162020-01-14 02:31:41 -06001132 return CmdHandler::ccOnlyResponse(request, PLDM_INVALID_FILE_TYPE);
1133 }
1134
1135 rc = handler->newFileAvailable(length);
1136 auto responsePtr = reinterpret_cast<pldm_msg*>(response.data());
Patrick Williams16c2a0a2024-08-16 15:20:59 -04001137 int responseCode =
1138 encode_new_file_resp(request->hdr.instance_id, rc, responsePtr);
Riya Dixit8394c452024-04-06 12:15:23 -05001139 if (responseCode != PLDM_SUCCESS)
1140 {
1141 error(
1142 "Failed to encode new file available response, response code '{RC}'",
1143 "RC", responseCode);
1144 }
Sampa Misra18967162020-01-14 02:31:41 -06001145 return response;
1146}
1147
Deepak Kodihallibc669f12019-11-28 08:52:07 -06001148} // namespace oem_ibm
Jinu Joy Thomas7f57f442019-06-13 20:38:49 +05301149} // namespace responder
1150} // namespace pldm