blob: 5e71c807bfddef984640c40725b270f78d89e2b3 [file] [log] [blame]
Andrew Jefferyb0c1d202023-11-07 22:08:44 +10301#include <libpldm/base.h>
2#include <libpldm/pldm_types.h>
3
Andrew Jeffery9c766792022-08-10 23:12:49 +09304#include <array>
Manojkiran Eda9a8e4972022-11-28 16:38:21 +05305#include <cstdint>
Andrew Jeffery9c766792022-08-10 23:12:49 +09306#include <cstring>
7#include <vector>
8
Andrew Jeffery9c766792022-08-10 23:12:49 +09309#include <gmock/gmock.h>
10#include <gtest/gtest.h>
11
12using testing::ElementsAreArray;
13
14constexpr auto hdrSize = sizeof(pldm_msg_hdr);
15
16TEST(PackPLDMMessage, BadPathTest)
17{
18 struct pldm_header_info hdr;
19 struct pldm_header_info* hdr_ptr = NULL;
20 pldm_msg_hdr msg{};
21
22 // PLDM header information pointer is NULL
23 auto rc = pack_pldm_header(hdr_ptr, &msg);
24 EXPECT_EQ(rc, PLDM_ERROR_INVALID_DATA);
25
26 // PLDM message pointer is NULL
27 rc = pack_pldm_header(&hdr, nullptr);
28 EXPECT_EQ(rc, PLDM_ERROR_INVALID_DATA);
29
30 // PLDM header information pointer and PLDM message pointer is NULL
31 rc = pack_pldm_header(hdr_ptr, nullptr);
32 EXPECT_EQ(rc, PLDM_ERROR_INVALID_DATA);
33
34 // RESERVED message type
35 hdr.msg_type = PLDM_RESERVED;
36 rc = pack_pldm_header(&hdr, &msg);
37 EXPECT_EQ(rc, PLDM_ERROR_INVALID_DATA);
38
39 // Instance ID out of range
40 hdr.msg_type = PLDM_REQUEST;
41 hdr.instance = 32;
42 rc = pack_pldm_header(&hdr, &msg);
43 EXPECT_EQ(rc, PLDM_ERROR_INVALID_DATA);
44
45 // PLDM type out of range
46 hdr.msg_type = PLDM_REQUEST;
47 hdr.instance = 31;
48 hdr.pldm_type = 64;
49 rc = pack_pldm_header(&hdr, &msg);
50 EXPECT_EQ(rc, PLDM_ERROR_INVALID_PLDM_TYPE);
51}
52
53TEST(PackPLDMMessage, RequestMessageGoodPath)
54{
55 struct pldm_header_info hdr;
56 pldm_msg_hdr msg{};
57
58 // Message type is REQUEST and lower range of the field values
59 hdr.msg_type = PLDM_REQUEST;
60 hdr.instance = 0;
61 hdr.pldm_type = 0;
62 hdr.command = 0;
63
64 auto rc = pack_pldm_header(&hdr, &msg);
65 EXPECT_EQ(rc, PLDM_SUCCESS);
66 EXPECT_EQ(msg.request, 1);
67 EXPECT_EQ(msg.datagram, 0);
68 EXPECT_EQ(msg.instance_id, 0);
69 EXPECT_EQ(msg.type, 0);
70 EXPECT_EQ(msg.command, 0);
71
72 // Message type is REQUEST and upper range of the field values
73 hdr.instance = 31;
74 hdr.pldm_type = 63;
75 hdr.command = 255;
76
77 rc = pack_pldm_header(&hdr, &msg);
78 EXPECT_EQ(rc, PLDM_SUCCESS);
79 EXPECT_EQ(msg.request, 1);
80 EXPECT_EQ(msg.datagram, 0);
81 EXPECT_EQ(msg.instance_id, 31);
82 EXPECT_EQ(msg.type, 63);
83 EXPECT_EQ(msg.command, 255);
84
85 // Message type is PLDM_ASYNC_REQUEST_NOTIFY
86 hdr.msg_type = PLDM_ASYNC_REQUEST_NOTIFY;
87
88 rc = pack_pldm_header(&hdr, &msg);
89 EXPECT_EQ(rc, PLDM_SUCCESS);
90 EXPECT_EQ(msg.request, 1);
91 EXPECT_EQ(msg.datagram, 1);
92 EXPECT_EQ(msg.instance_id, 31);
93 EXPECT_EQ(msg.type, 63);
94 EXPECT_EQ(msg.command, 255);
95}
96
97TEST(PackPLDMMessage, ResponseMessageGoodPath)
98{
99 struct pldm_header_info hdr;
100 pldm_msg_hdr msg{};
101
102 // Message type is PLDM_RESPONSE and lower range of the field values
103 hdr.msg_type = PLDM_RESPONSE;
104 hdr.instance = 0;
105 hdr.pldm_type = 0;
106 hdr.command = 0;
107
108 auto rc = pack_pldm_header(&hdr, &msg);
109 EXPECT_EQ(rc, PLDM_SUCCESS);
110 EXPECT_EQ(msg.request, 0);
111 EXPECT_EQ(msg.datagram, 0);
112 EXPECT_EQ(msg.instance_id, 0);
113 EXPECT_EQ(msg.type, 0);
114 EXPECT_EQ(msg.command, 0);
115
116 // Message type is PLDM_RESPONSE and upper range of the field values
117 hdr.instance = 31;
118 hdr.pldm_type = 63;
119 hdr.command = 255;
120
121 rc = pack_pldm_header(&hdr, &msg);
122 EXPECT_EQ(rc, PLDM_SUCCESS);
123 EXPECT_EQ(msg.request, 0);
124 EXPECT_EQ(msg.datagram, 0);
125 EXPECT_EQ(msg.instance_id, 31);
126 EXPECT_EQ(msg.type, 63);
127 EXPECT_EQ(msg.command, 255);
128}
129
130TEST(UnpackPLDMMessage, BadPathTest)
131{
132 struct pldm_header_info hdr;
133
134 // PLDM message pointer is NULL
135 auto rc = unpack_pldm_header(nullptr, &hdr);
136 EXPECT_EQ(rc, PLDM_ERROR_INVALID_DATA);
137}
138
139TEST(UnpackPLDMMessage, RequestMessageGoodPath)
140{
141 struct pldm_header_info hdr;
142 pldm_msg_hdr msg{};
143
144 // Unpack PLDM request message and lower range of field values
145 msg.request = 1;
146 auto rc = unpack_pldm_header(&msg, &hdr);
147 EXPECT_EQ(rc, PLDM_SUCCESS);
148 EXPECT_EQ(hdr.msg_type, PLDM_REQUEST);
149 EXPECT_EQ(hdr.instance, 0);
150 EXPECT_EQ(hdr.pldm_type, 0);
151 EXPECT_EQ(hdr.command, 0);
152
153 // Unpack PLDM async request message and lower range of field values
154 msg.datagram = 1;
155 rc = unpack_pldm_header(&msg, &hdr);
156 EXPECT_EQ(rc, PLDM_SUCCESS);
157 EXPECT_EQ(hdr.msg_type, PLDM_ASYNC_REQUEST_NOTIFY);
158
159 // Unpack PLDM request message and upper range of field values
160 msg.datagram = 0;
161 msg.instance_id = 31;
162 msg.type = 63;
163 msg.command = 255;
164 rc = unpack_pldm_header(&msg, &hdr);
165 EXPECT_EQ(rc, PLDM_SUCCESS);
166 EXPECT_EQ(hdr.msg_type, PLDM_REQUEST);
167 EXPECT_EQ(hdr.instance, 31);
168 EXPECT_EQ(hdr.pldm_type, 63);
169 EXPECT_EQ(hdr.command, 255);
170}
171
172TEST(UnpackPLDMMessage, ResponseMessageGoodPath)
173{
174 struct pldm_header_info hdr;
175 pldm_msg_hdr msg{};
176
177 // Unpack PLDM response message and lower range of field values
178 auto rc = unpack_pldm_header(&msg, &hdr);
179 EXPECT_EQ(rc, PLDM_SUCCESS);
180 EXPECT_EQ(hdr.msg_type, PLDM_RESPONSE);
181 EXPECT_EQ(hdr.instance, 0);
182 EXPECT_EQ(hdr.pldm_type, 0);
183 EXPECT_EQ(hdr.command, 0);
184
185 // Unpack PLDM response message and upper range of field values
186 msg.instance_id = 31;
187 msg.type = 63;
188 msg.command = 255;
189 rc = unpack_pldm_header(&msg, &hdr);
190 EXPECT_EQ(rc, PLDM_SUCCESS);
191 EXPECT_EQ(hdr.msg_type, PLDM_RESPONSE);
192 EXPECT_EQ(hdr.instance, 31);
193 EXPECT_EQ(hdr.pldm_type, 63);
194 EXPECT_EQ(hdr.command, 255);
195}
196
197TEST(GetPLDMCommands, testEncodeRequest)
198{
199 uint8_t pldmType = 0x05;
Pavithra Barithayadc7d3b52024-02-06 23:46:49 -0600200 ver32_t version{0xff, 0xff, 0xff, 0xff};
Andrew Jeffery9c766792022-08-10 23:12:49 +0930201 std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_COMMANDS_REQ_BYTES>
202 requestMsg{};
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930203 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930204 auto request = reinterpret_cast<pldm_msg*>(requestMsg.data());
205
206 auto rc = encode_get_commands_req(0, pldmType, version, request);
207 EXPECT_EQ(rc, PLDM_SUCCESS);
208 EXPECT_EQ(0, memcmp(request->payload, &pldmType, sizeof(pldmType)));
209 EXPECT_EQ(0, memcmp(request->payload + sizeof(pldmType), &version,
210 sizeof(version)));
211}
212
213TEST(GetPLDMCommands, testDecodeRequest)
214{
215 uint8_t pldmType = 0x05;
Pavithra Barithayadc7d3b52024-02-06 23:46:49 -0600216 ver32_t version{0xff, 0xff, 0xff, 0xff};
Andrew Jeffery9c766792022-08-10 23:12:49 +0930217 uint8_t pldmTypeOut{};
Pavithra Barithayadc7d3b52024-02-06 23:46:49 -0600218 ver32_t versionOut{0xff, 0xff, 0xff, 0xff};
Andrew Jeffery9c766792022-08-10 23:12:49 +0930219 std::array<uint8_t, hdrSize + PLDM_GET_COMMANDS_REQ_BYTES> requestMsg{};
220
221 memcpy(requestMsg.data() + hdrSize, &pldmType, sizeof(pldmType));
222 memcpy(requestMsg.data() + sizeof(pldmType) + hdrSize, &version,
223 sizeof(version));
224
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930225 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930226 auto request = reinterpret_cast<pldm_msg*>(requestMsg.data());
227 auto rc = decode_get_commands_req(request, requestMsg.size() - hdrSize,
228 &pldmTypeOut, &versionOut);
229
230 EXPECT_EQ(rc, PLDM_SUCCESS);
231 EXPECT_EQ(pldmTypeOut, pldmType);
232 EXPECT_EQ(0, memcmp(&versionOut, &version, sizeof(version)));
233}
234
235TEST(GetPLDMCommands, testEncodeResponse)
236{
237 uint8_t completionCode = 0;
238 std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_COMMANDS_RESP_BYTES>
239 responseMsg{};
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930240 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930241 auto response = reinterpret_cast<pldm_msg*>(responseMsg.data());
242 std::array<bitfield8_t, PLDM_MAX_CMDS_PER_TYPE / 8> commands{};
243 commands[0].byte = 1;
244 commands[1].byte = 2;
245 commands[2].byte = 3;
246
247 auto rc =
248 encode_get_commands_resp(0, PLDM_SUCCESS, commands.data(), response);
249 EXPECT_EQ(rc, PLDM_SUCCESS);
250 uint8_t* payload_ptr = response->payload;
251 EXPECT_EQ(completionCode, payload_ptr[0]);
252 EXPECT_EQ(1, payload_ptr[sizeof(completionCode)]);
253 EXPECT_EQ(2,
254 payload_ptr[sizeof(completionCode) + sizeof(commands[0].byte)]);
255 EXPECT_EQ(3, payload_ptr[sizeof(completionCode) + sizeof(commands[0].byte) +
256 sizeof(commands[1].byte)]);
257}
258
259TEST(GetPLDMTypes, testEncodeResponse)
260{
261 uint8_t completionCode = 0;
262 std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_TYPES_RESP_BYTES>
263 responseMsg{};
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930264 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930265 auto response = reinterpret_cast<pldm_msg*>(responseMsg.data());
266 std::array<bitfield8_t, PLDM_MAX_TYPES / 8> types{};
267 types[0].byte = 1;
268 types[1].byte = 2;
269 types[2].byte = 3;
270
271 auto rc = encode_get_types_resp(0, PLDM_SUCCESS, types.data(), response);
272 EXPECT_EQ(rc, PLDM_SUCCESS);
273 uint8_t* payload_ptr = response->payload;
274 EXPECT_EQ(completionCode, payload_ptr[0]);
275 EXPECT_EQ(1, payload_ptr[sizeof(completionCode)]);
276 EXPECT_EQ(2, payload_ptr[sizeof(completionCode) + sizeof(types[0].byte)]);
277 EXPECT_EQ(3, payload_ptr[sizeof(completionCode) + sizeof(types[0].byte) +
278 sizeof(types[1].byte)]);
279}
280
281TEST(GetPLDMTypes, testGoodDecodeResponse)
282{
283 std::array<uint8_t, hdrSize + PLDM_GET_TYPES_RESP_BYTES> responseMsg{};
284 responseMsg[1 + hdrSize] = 1;
285 responseMsg[2 + hdrSize] = 2;
286 responseMsg[3 + hdrSize] = 3;
287 std::array<bitfield8_t, PLDM_MAX_TYPES / 8> outTypes{};
288
289 uint8_t completion_code;
290 responseMsg[hdrSize] = PLDM_SUCCESS;
291
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930292 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930293 auto response = reinterpret_cast<pldm_msg*>(responseMsg.data());
294
295 auto rc = decode_get_types_resp(response, responseMsg.size() - hdrSize,
296 &completion_code, outTypes.data());
297
298 EXPECT_EQ(rc, PLDM_SUCCESS);
299 EXPECT_EQ(completion_code, PLDM_SUCCESS);
300 EXPECT_EQ(responseMsg[1 + hdrSize], outTypes[0].byte);
301 EXPECT_EQ(responseMsg[2 + hdrSize], outTypes[1].byte);
302 EXPECT_EQ(responseMsg[3 + hdrSize], outTypes[2].byte);
303}
304
305TEST(GetPLDMTypes, testBadDecodeResponse)
306{
307 std::array<uint8_t, hdrSize + PLDM_GET_TYPES_RESP_BYTES> responseMsg{};
308 responseMsg[1 + hdrSize] = 1;
309 responseMsg[2 + hdrSize] = 2;
310 responseMsg[3 + hdrSize] = 3;
311 std::array<bitfield8_t, PLDM_MAX_TYPES / 8> outTypes{};
312
313 uint8_t retcompletion_code = 0;
314 responseMsg[hdrSize] = PLDM_SUCCESS;
315
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930316 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930317 auto response = reinterpret_cast<pldm_msg*>(responseMsg.data());
318
319 auto rc = decode_get_types_resp(response, responseMsg.size() - hdrSize - 1,
320 &retcompletion_code, outTypes.data());
321
322 EXPECT_EQ(rc, PLDM_ERROR_INVALID_LENGTH);
323}
324
325TEST(GetPLDMCommands, testGoodDecodeResponse)
326{
327 std::array<uint8_t, hdrSize + PLDM_GET_COMMANDS_RESP_BYTES> responseMsg{};
328 responseMsg[1 + hdrSize] = 1;
329 responseMsg[2 + hdrSize] = 2;
330 responseMsg[3 + hdrSize] = 3;
331 std::array<bitfield8_t, PLDM_MAX_CMDS_PER_TYPE / 8> outTypes{};
332
333 uint8_t completion_code;
334 responseMsg[hdrSize] = PLDM_SUCCESS;
335
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930336 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930337 auto response = reinterpret_cast<pldm_msg*>(responseMsg.data());
338
339 auto rc = decode_get_commands_resp(response, responseMsg.size() - hdrSize,
340 &completion_code, outTypes.data());
341
342 EXPECT_EQ(rc, PLDM_SUCCESS);
343 EXPECT_EQ(completion_code, PLDM_SUCCESS);
344 EXPECT_EQ(responseMsg[1 + hdrSize], outTypes[0].byte);
345 EXPECT_EQ(responseMsg[2 + hdrSize], outTypes[1].byte);
346 EXPECT_EQ(responseMsg[3 + hdrSize], outTypes[2].byte);
347}
348
349TEST(GetPLDMCommands, testBadDecodeResponse)
350{
351 std::array<uint8_t, hdrSize + PLDM_GET_COMMANDS_RESP_BYTES> responseMsg{};
352 responseMsg[1 + hdrSize] = 1;
353 responseMsg[2 + hdrSize] = 2;
354 responseMsg[3 + hdrSize] = 3;
355 std::array<bitfield8_t, PLDM_MAX_CMDS_PER_TYPE / 8> outTypes{};
356
357 uint8_t retcompletion_code = 0;
358 responseMsg[hdrSize] = PLDM_SUCCESS;
359
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930360 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930361 auto response = reinterpret_cast<pldm_msg*>(responseMsg.data());
362
363 auto rc =
364 decode_get_commands_resp(response, responseMsg.size() - hdrSize - 1,
365 &retcompletion_code, outTypes.data());
366
367 EXPECT_EQ(rc, PLDM_ERROR_INVALID_LENGTH);
368}
369
370TEST(GetPLDMVersion, testGoodEncodeRequest)
371{
372 std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_VERSION_REQ_BYTES>
373 requestMsg{};
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930374 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930375 auto request = reinterpret_cast<pldm_msg*>(requestMsg.data());
376 uint8_t pldmType = 0x03;
377 uint32_t transferHandle = 0x0;
378 uint8_t opFlag = 0x01;
379
380 auto rc =
381 encode_get_version_req(0, transferHandle, opFlag, pldmType, request);
382 EXPECT_EQ(rc, PLDM_SUCCESS);
383 EXPECT_EQ(
384 0, memcmp(request->payload, &transferHandle, sizeof(transferHandle)));
385 EXPECT_EQ(0, memcmp(request->payload + sizeof(transferHandle), &opFlag,
386 sizeof(opFlag)));
387 EXPECT_EQ(0,
388 memcmp(request->payload + sizeof(transferHandle) + sizeof(opFlag),
389 &pldmType, sizeof(pldmType)));
390}
391
392TEST(GetPLDMVersion, testBadEncodeRequest)
393{
394 uint8_t pldmType = 0x03;
395 uint32_t transferHandle = 0x0;
396 uint8_t opFlag = 0x01;
397
398 auto rc =
399 encode_get_version_req(0, transferHandle, opFlag, pldmType, nullptr);
400
401 EXPECT_EQ(rc, PLDM_ERROR_INVALID_DATA);
402}
403
404TEST(GetPLDMVersion, testEncodeResponse)
405{
406 uint8_t completionCode = 0;
407 uint32_t transferHandle = 0;
408 uint8_t flag = PLDM_START_AND_END;
409 std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_VERSION_RESP_BYTES>
410 responseMsg{};
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930411 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930412 auto response = reinterpret_cast<pldm_msg*>(responseMsg.data());
Pavithra Barithayadc7d3b52024-02-06 23:46:49 -0600413 ver32_t version = {0xff, 0xff, 0xff, 0xff};
Andrew Jeffery9c766792022-08-10 23:12:49 +0930414
415 auto rc = encode_get_version_resp(0, PLDM_SUCCESS, 0, PLDM_START_AND_END,
416 &version, sizeof(ver32_t), response);
417
418 EXPECT_EQ(rc, PLDM_SUCCESS);
419 EXPECT_EQ(completionCode, response->payload[0]);
420 EXPECT_EQ(0, memcmp(response->payload + sizeof(response->payload[0]),
421 &transferHandle, sizeof(transferHandle)));
422 EXPECT_EQ(0, memcmp(response->payload + sizeof(response->payload[0]) +
423 sizeof(transferHandle),
424 &flag, sizeof(flag)));
425 EXPECT_EQ(0, memcmp(response->payload + sizeof(response->payload[0]) +
426 sizeof(transferHandle) + sizeof(flag),
427 &version, sizeof(version)));
428}
429
430TEST(GetPLDMVersion, testDecodeRequest)
431{
432 std::array<uint8_t, hdrSize + PLDM_GET_VERSION_REQ_BYTES> requestMsg{};
433 uint32_t transferHandle = 0x0;
434 uint32_t retTransferHandle = 0x0;
435 uint8_t flag = PLDM_GET_FIRSTPART;
436 uint8_t retFlag = PLDM_GET_FIRSTPART;
437 uint8_t pldmType = PLDM_BASE;
438 uint8_t retType = PLDM_BASE;
439
440 memcpy(requestMsg.data() + hdrSize, &transferHandle,
441 sizeof(transferHandle));
442 memcpy(requestMsg.data() + sizeof(transferHandle) + hdrSize, &flag,
443 sizeof(flag));
444 memcpy(requestMsg.data() + sizeof(transferHandle) + sizeof(flag) + hdrSize,
445 &pldmType, sizeof(pldmType));
446
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930447 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930448 auto request = reinterpret_cast<pldm_msg*>(requestMsg.data());
449
450 auto rc = decode_get_version_req(request, requestMsg.size() - hdrSize,
451 &retTransferHandle, &retFlag, &retType);
452
453 EXPECT_EQ(rc, PLDM_SUCCESS);
454 EXPECT_EQ(transferHandle, retTransferHandle);
455 EXPECT_EQ(flag, retFlag);
456 EXPECT_EQ(pldmType, retType);
457}
458
459TEST(GetPLDMVersion, testDecodeResponse)
460{
461 std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_VERSION_RESP_BYTES>
462 responseMsg{};
463 uint32_t transferHandle = 0x0;
464 uint32_t retTransferHandle = 0x0;
465 uint8_t flag = PLDM_START_AND_END;
466 uint8_t retFlag = PLDM_START_AND_END;
467 uint8_t completionCode = 0;
Pavithra Barithayadc7d3b52024-02-06 23:46:49 -0600468 ver32_t version = {0xff, 0xff, 0xff, 0xff};
Andrew Jeffery9c766792022-08-10 23:12:49 +0930469 ver32_t versionOut;
470 uint8_t completion_code;
471
472 memcpy(responseMsg.data() + sizeof(completionCode) + hdrSize,
473 &transferHandle, sizeof(transferHandle));
474 memcpy(responseMsg.data() + sizeof(completionCode) +
475 sizeof(transferHandle) + hdrSize,
476 &flag, sizeof(flag));
477 memcpy(responseMsg.data() + sizeof(completionCode) +
478 sizeof(transferHandle) + sizeof(flag) + hdrSize,
479 &version, sizeof(version));
480
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930481 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930482 auto response = reinterpret_cast<pldm_msg*>(responseMsg.data());
483
484 auto rc = decode_get_version_resp(response, responseMsg.size() - hdrSize,
485 &completion_code, &retTransferHandle,
486 &retFlag, &versionOut);
487 EXPECT_EQ(rc, PLDM_SUCCESS);
488 EXPECT_EQ(transferHandle, retTransferHandle);
489 EXPECT_EQ(flag, retFlag);
490
491 EXPECT_EQ(versionOut.major, version.major);
492 EXPECT_EQ(versionOut.minor, version.minor);
493 EXPECT_EQ(versionOut.update, version.update);
494 EXPECT_EQ(versionOut.alpha, version.alpha);
495}
496
497TEST(GetTID, testEncodeRequest)
498{
499 pldm_msg request{};
500
501 auto rc = encode_get_tid_req(0, &request);
502 ASSERT_EQ(rc, PLDM_SUCCESS);
503}
504
505TEST(GetTID, testEncodeResponse)
506{
507 uint8_t completionCode = 0;
508 std::array<uint8_t, sizeof(pldm_msg_hdr) + PLDM_GET_TID_RESP_BYTES>
509 responseMsg{};
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930510 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930511 auto response = reinterpret_cast<pldm_msg*>(responseMsg.data());
512 uint8_t tid = 1;
513
514 auto rc = encode_get_tid_resp(0, PLDM_SUCCESS, tid, response);
515 EXPECT_EQ(rc, PLDM_SUCCESS);
516 uint8_t* payload = response->payload;
517 EXPECT_EQ(completionCode, payload[0]);
518 EXPECT_EQ(1, payload[sizeof(completionCode)]);
519}
520
521TEST(GetTID, testDecodeResponse)
522{
523 std::array<uint8_t, hdrSize + PLDM_GET_TID_RESP_BYTES> responseMsg{};
524 responseMsg[1 + hdrSize] = 1;
525
526 uint8_t tid;
527 uint8_t completion_code;
528 responseMsg[hdrSize] = PLDM_SUCCESS;
529
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930530 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930531 auto response = reinterpret_cast<pldm_msg*>(responseMsg.data());
532
533 auto rc = decode_get_tid_resp(response, responseMsg.size() - hdrSize,
534 &completion_code, &tid);
535
536 EXPECT_EQ(rc, PLDM_SUCCESS);
537 EXPECT_EQ(completion_code, PLDM_SUCCESS);
538 EXPECT_EQ(tid, 1);
539}
540
541TEST(MultipartReceive, testDecodeRequestPass)
542{
543 constexpr uint8_t kPldmType = PLDM_BASE;
544 constexpr uint8_t kFlag = PLDM_XFER_FIRST_PART;
545 constexpr uint32_t kTransferCtx = 0x01;
546 constexpr uint32_t kTransferHandle = 0x10;
547 constexpr uint32_t kSectionOffset = 0x0;
548 constexpr uint32_t kSectionLength = 0x10;
549 uint8_t pldm_type = 0x0;
550 uint8_t flag = PLDM_GET_FIRSTPART;
551 uint32_t transfer_ctx;
552 uint32_t transfer_handle;
553 uint32_t section_offset;
554 uint32_t section_length;
555
556 // Header values don't matter for this test.
557 pldm_msg_hdr hdr{};
558 // Assign values to the packet struct and memcpy to ensure correct byte
559 // ordering.
560 pldm_multipart_receive_req req_pkt = {
561 .pldm_type = kPldmType,
562 .transfer_opflag = kFlag,
563 .transfer_ctx = kTransferCtx,
564 .transfer_handle = kTransferHandle,
565 .section_offset = kSectionOffset,
566 .section_length = kSectionLength,
567 };
568 std::vector<uint8_t> req(sizeof(hdr) + PLDM_MULTIPART_RECEIVE_REQ_BYTES);
569 std::memcpy(req.data(), &hdr, sizeof(hdr));
570 std::memcpy(req.data() + sizeof(hdr), &req_pkt, sizeof(req_pkt));
571
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930572 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930573 pldm_msg* pldm_request = reinterpret_cast<pldm_msg*>(req.data());
574 int rc = decode_multipart_receive_req(
575 pldm_request, req.size() - hdrSize, &pldm_type, &flag, &transfer_ctx,
576 &transfer_handle, &section_offset, &section_length);
577
578 EXPECT_EQ(rc, PLDM_SUCCESS);
579 EXPECT_EQ(pldm_type, kPldmType);
580 EXPECT_EQ(flag, kFlag);
581 EXPECT_EQ(transfer_ctx, kTransferCtx);
582 EXPECT_EQ(transfer_handle, kTransferHandle);
583 EXPECT_EQ(section_offset, kSectionOffset);
584 EXPECT_EQ(section_length, kSectionLength);
585}
586
587TEST(MultipartReceive, testDecodeRequestFailNullData)
588{
589 EXPECT_EQ(decode_multipart_receive_req(NULL, 0, NULL, NULL, NULL, NULL,
590 NULL, NULL),
591 PLDM_ERROR_INVALID_DATA);
592}
593
594TEST(MultipartReceive, testDecodeRequestFailBadLength)
595{
596 constexpr uint8_t kPldmType = PLDM_BASE;
597 constexpr uint8_t kFlag = PLDM_XFER_FIRST_PART;
598 uint8_t pldm_type;
599 uint8_t flag;
600 uint32_t transfer_ctx;
601 uint32_t transfer_handle;
602 uint32_t section_offset;
603 uint32_t section_length;
604
605 // Header values don't matter for this test.
606 pldm_msg_hdr hdr{};
607 // Assign values to the packet struct and memcpy to ensure correct byte
608 // ordering.
609 pldm_multipart_receive_req req_pkt{};
610 req_pkt.pldm_type = kPldmType;
611 req_pkt.transfer_opflag = kFlag;
612
613 std::vector<uint8_t> req(sizeof(hdr) + PLDM_MULTIPART_RECEIVE_REQ_BYTES);
614 std::memcpy(req.data(), &hdr, sizeof(hdr));
615 std::memcpy(req.data() + sizeof(hdr), &req_pkt, sizeof(req_pkt));
616
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930617 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930618 pldm_msg* pldm_request = reinterpret_cast<pldm_msg*>(req.data());
619 EXPECT_EQ(decode_multipart_receive_req(
620 pldm_request, (req.size() - hdrSize) + 1, &pldm_type, &flag,
621 &transfer_ctx, &transfer_handle, &section_offset,
622 &section_length),
623 PLDM_ERROR_INVALID_LENGTH);
624}
625
626TEST(MultipartReceive, testDecodeRequestFailBadPldmType)
627{
628 constexpr uint8_t kPldmType = 0xff;
629 constexpr uint8_t kFlag = PLDM_XFER_FIRST_PART;
630 uint8_t pldm_type;
631 uint8_t flag;
632 uint32_t transfer_ctx;
633 uint32_t transfer_handle;
634 uint32_t section_offset;
635 uint32_t section_length;
636
637 // Header values don't matter for this test.
638 pldm_msg_hdr hdr{};
639 // Assign values to the packet struct and memcpy to ensure correct byte
640 // ordering.
641 pldm_multipart_receive_req req_pkt{};
642 req_pkt.pldm_type = kPldmType;
643 req_pkt.transfer_opflag = kFlag;
644
645 std::vector<uint8_t> req(sizeof(hdr) + PLDM_MULTIPART_RECEIVE_REQ_BYTES);
646 std::memcpy(req.data(), &hdr, sizeof(hdr));
647 std::memcpy(req.data() + sizeof(hdr), &req_pkt, sizeof(req_pkt));
648
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930649 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930650 pldm_msg* pldm_request = reinterpret_cast<pldm_msg*>(req.data());
651 EXPECT_EQ(decode_multipart_receive_req(pldm_request, req.size() - hdrSize,
652 &pldm_type, &flag, &transfer_ctx,
653 &transfer_handle, &section_offset,
654 &section_length),
655 PLDM_ERROR_INVALID_PLDM_TYPE);
656}
657
658TEST(MultipartReceive, testDecodeRequestFailBadTransferFlag)
659{
660 constexpr uint8_t kPldmType = PLDM_BASE;
661 constexpr uint8_t kFlag = PLDM_XFER_CURRENT_PART + 0x10;
662 uint8_t pldm_type;
663 uint8_t flag;
664 uint32_t transfer_ctx;
665 uint32_t transfer_handle;
666 uint32_t section_offset;
667 uint32_t section_length;
668
669 // Header values don't matter for this test.
670 pldm_msg_hdr hdr{};
671 // Assign values to the packet struct and memcpy to ensure correct byte
672 // ordering.
673 pldm_multipart_receive_req req_pkt{};
674 req_pkt.pldm_type = kPldmType;
675 req_pkt.transfer_opflag = kFlag;
676
677 std::vector<uint8_t> req(sizeof(hdr) + PLDM_MULTIPART_RECEIVE_REQ_BYTES);
678 std::memcpy(req.data(), &hdr, sizeof(hdr));
679 std::memcpy(req.data() + sizeof(hdr), &req_pkt, sizeof(req_pkt));
680
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930681 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930682 pldm_msg* pldm_request = reinterpret_cast<pldm_msg*>(req.data());
683 EXPECT_EQ(decode_multipart_receive_req(pldm_request, req.size() - hdrSize,
684 &pldm_type, &flag, &transfer_ctx,
685 &transfer_handle, &section_offset,
686 &section_length),
687 PLDM_INVALID_TRANSFER_OPERATION_FLAG);
688}
689
690TEST(MultipartReceive, testDecodeRequestFailBadOffset)
691{
692 constexpr uint8_t kPldmType = PLDM_BASE;
693 constexpr uint8_t kFlag = PLDM_XFER_NEXT_PART;
694 constexpr uint32_t kTransferHandle = 0x01;
695 constexpr uint32_t kSectionOffset = 0x0;
696 uint8_t pldm_type;
697 uint8_t flag;
698 uint32_t transfer_ctx;
699 uint32_t transfer_handle;
700 uint32_t section_offset;
701 uint32_t section_length;
702
703 // Header values don't matter for this test.
704 pldm_msg_hdr hdr{};
705 // Assign values to the packet struct and memcpy to ensure correct byte
706 // ordering.
707 pldm_multipart_receive_req req_pkt{};
708 req_pkt.pldm_type = kPldmType;
709 req_pkt.transfer_opflag = kFlag;
710 req_pkt.transfer_handle = kTransferHandle;
711 req_pkt.section_offset = kSectionOffset;
712
713 std::vector<uint8_t> req(sizeof(hdr) + PLDM_MULTIPART_RECEIVE_REQ_BYTES);
714 std::memcpy(req.data(), &hdr, sizeof(hdr));
715 std::memcpy(req.data() + sizeof(hdr), &req_pkt, sizeof(req_pkt));
716
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930717 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930718 pldm_msg* pldm_request = reinterpret_cast<pldm_msg*>(req.data());
719 EXPECT_EQ(decode_multipart_receive_req(pldm_request, req.size() - hdrSize,
720 &pldm_type, &flag, &transfer_ctx,
721 &transfer_handle, &section_offset,
722 &section_length),
723 PLDM_ERROR_INVALID_DATA);
724}
725
726TEST(MultipartReceive, testDecodeRequestFailBadHandle)
727{
728 constexpr uint8_t kPldmType = PLDM_BASE;
729 constexpr uint8_t kFlag = PLDM_XFER_NEXT_PART;
730 constexpr uint32_t kSectionOffset = 0x100;
731 constexpr uint32_t kTransferHandle = 0x0;
732 uint8_t pldm_type;
733 uint8_t flag;
734 uint32_t transfer_ctx;
735 uint32_t transfer_handle;
736 uint32_t section_offset;
737 uint32_t section_length;
738
739 // Header values don't matter for this test.
740 pldm_msg_hdr hdr{};
741 // Assign values to the packet struct and memcpy to ensure correct byte
742 // ordering.
743 pldm_multipart_receive_req req_pkt{};
744 req_pkt.pldm_type = kPldmType;
745 req_pkt.transfer_opflag = kFlag;
746 req_pkt.transfer_handle = kTransferHandle;
747 req_pkt.section_offset = kSectionOffset;
748
749 std::vector<uint8_t> req(sizeof(hdr) + PLDM_MULTIPART_RECEIVE_REQ_BYTES);
750 std::memcpy(req.data(), &hdr, sizeof(hdr));
751 std::memcpy(req.data() + sizeof(hdr), &req_pkt, sizeof(req_pkt));
752
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930753 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930754 pldm_msg* pldm_request = reinterpret_cast<pldm_msg*>(req.data());
755 EXPECT_EQ(decode_multipart_receive_req(pldm_request, req.size() - hdrSize,
756 &pldm_type, &flag, &transfer_ctx,
757 &transfer_handle, &section_offset,
758 &section_length),
759 PLDM_ERROR_INVALID_DATA);
760}
761
762TEST(CcOnlyResponse, testEncode)
763{
764 struct pldm_msg responseMsg;
765
766 auto rc =
767 encode_cc_only_resp(0 /*instance id*/, 1 /*pldm type*/, 2 /*command*/,
Manojkiran Eda9e3a5d42024-06-17 16:06:42 +0530768 3 /*completion code*/, &responseMsg);
Andrew Jeffery9c766792022-08-10 23:12:49 +0930769 EXPECT_EQ(rc, PLDM_SUCCESS);
770
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930771 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Andrew Jeffery9c766792022-08-10 23:12:49 +0930772 auto p = reinterpret_cast<uint8_t*>(&responseMsg);
773 EXPECT_THAT(std::vector<uint8_t>(p, p + sizeof(responseMsg)),
774 ElementsAreArray({0, 1, 2, 3}));
775
776 rc = encode_cc_only_resp(PLDM_INSTANCE_MAX + 1, 1, 2, 3, &responseMsg);
777 EXPECT_EQ(rc, PLDM_ERROR_INVALID_DATA);
778
779 rc = encode_cc_only_resp(0, 1, 2, 3, nullptr);
780 EXPECT_EQ(rc, PLDM_ERROR_INVALID_DATA);
781}
Gilbert Chen6c9c9172022-10-18 17:07:29 +0800782
783TEST(SetTID, testGoodEncodeRequest)
784{
785 uint8_t instanceId = 0;
786 uint8_t tid = 0x01;
787 std::array<uint8_t, sizeof(pldm_msg_hdr) + sizeof(tid)> requestMsg{};
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930788 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Gilbert Chen6c9c9172022-10-18 17:07:29 +0800789 auto request = reinterpret_cast<pldm_msg*>(requestMsg.data());
790
791 auto rc = encode_set_tid_req(instanceId, tid, request);
792 ASSERT_EQ(rc, PLDM_SUCCESS);
793
794 EXPECT_EQ(request->hdr.command, PLDM_SET_TID);
795 EXPECT_EQ(request->hdr.type, PLDM_BASE);
796 EXPECT_EQ(request->hdr.request, 1);
797 EXPECT_EQ(request->hdr.datagram, 0);
798 EXPECT_EQ(request->hdr.instance_id, instanceId);
799 EXPECT_EQ(0, memcmp(request->payload, &tid, sizeof(tid)));
800}
801
802TEST(SetTID, testBadEncodeRequest)
803{
804 uint8_t tid = 0x01;
805 std::array<uint8_t, sizeof(pldm_msg_hdr) + sizeof(tid)> requestMsg{};
Andrew Jefferyd0ba43a2024-09-09 15:50:17 +0930806 // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
Gilbert Chen6c9c9172022-10-18 17:07:29 +0800807 auto request = reinterpret_cast<pldm_msg*>(requestMsg.data());
808
809 auto rc = encode_set_tid_req(0, tid, nullptr);
810 EXPECT_EQ(rc, PLDM_ERROR_INVALID_DATA);
811
812 rc = encode_set_tid_req(0, 0, request);
813 EXPECT_EQ(rc, PLDM_ERROR_INVALID_DATA);
814
815 rc = encode_set_tid_req(0, 0xff, request);
816 EXPECT_EQ(rc, PLDM_ERROR_INVALID_DATA);
817}
Andrew Jeffery91c06e92023-09-22 15:22:54 +0930818
819#ifdef LIBPLDM_API_TESTING
820TEST(PldmMsgHdr, correlateSuccess)
821{
822 static const struct pldm_msg_hdr req = {
823 .instance_id = 0,
824 .reserved = 0,
825 .datagram = 0,
826 .request = 1,
827 .type = 0,
828 .header_ver = 1,
829 .command = 0x01,
830 };
831 static const struct pldm_msg_hdr resp = {
832 .instance_id = 0,
833 .reserved = 0,
834 .datagram = 0,
835 .request = 0,
836 .type = 0,
837 .header_ver = 1,
838 .command = 0x01,
839 };
840
841 ASSERT_EQ(pldm_msg_hdr_correlate_response(&req, &resp), true);
842}
843#endif
844
845#ifdef LIBPLDM_API_TESTING
846TEST(PldmMsgHdr, correlateFailInstanceID)
847{
848 static const struct pldm_msg_hdr req = {
849 .instance_id = 0,
850 .reserved = 0,
851 .datagram = 0,
852 .request = 1,
853 .type = 0,
854 .header_ver = 1,
855 .command = 0x01,
856 };
857 static const struct pldm_msg_hdr resp = {
858 .instance_id = 1,
859 .reserved = 0,
860 .datagram = 0,
861 .request = 0,
862 .type = 0,
863 .header_ver = 1,
864 .command = 0x01,
865 };
866
867 ASSERT_EQ(pldm_msg_hdr_correlate_response(&req, &resp), false);
868}
869#endif
870
871#ifdef LIBPLDM_API_TESTING
872TEST(PldmMsgHdr, correlateFailRequest)
873{
874 static const struct pldm_msg_hdr req = {
875 .instance_id = 0,
876 .reserved = 0,
877 .datagram = 0,
878 .request = 1,
879 .type = 0,
880 .header_ver = 1,
881 .command = 0x01,
882 };
883 static const struct pldm_msg_hdr resp = {
884 .instance_id = 0,
885 .reserved = 0,
886 .datagram = 0,
887 .request = 1,
888 .type = 0,
889 .header_ver = 1,
890 .command = 0x01,
891 };
892
893 ASSERT_EQ(pldm_msg_hdr_correlate_response(&req, &resp), false);
894}
895#endif
896
897#ifdef LIBPLDM_API_TESTING
898TEST(PldmMsgHdr, correlateFailType)
899{
900 static const struct pldm_msg_hdr req = {
901 .instance_id = 0,
902 .reserved = 0,
903 .datagram = 0,
904 .request = 1,
905 .type = 0,
906 .header_ver = 1,
907 .command = 0x01,
908 };
909 static const struct pldm_msg_hdr resp = {
910 .instance_id = 0,
911 .reserved = 0,
912 .datagram = 0,
913 .request = 0,
914 .type = 1,
915 .header_ver = 1,
916 .command = 0x01,
917 };
918
919 ASSERT_EQ(pldm_msg_hdr_correlate_response(&req, &resp), false);
920}
921#endif
922
923#ifdef LIBPLDM_API_TESTING
924TEST(PldmMsgHdr, correlateFailCommand)
925{
926 static const struct pldm_msg_hdr req = {
927 .instance_id = 0,
928 .reserved = 0,
929 .datagram = 0,
930 .request = 1,
931 .type = 0,
932 .header_ver = 1,
933 .command = 0x01,
934 };
935 static const struct pldm_msg_hdr resp = {
936 .instance_id = 0,
937 .reserved = 0,
938 .datagram = 0,
939 .request = 0,
940 .type = 0,
941 .header_ver = 1,
942 .command = 0x02,
943 };
944
945 ASSERT_EQ(pldm_msg_hdr_correlate_response(&req, &resp), false);
946}
947#endif
948
949#ifdef LIBPLDM_API_TESTING
950TEST(PldmMsgHdr, correlateFailRequestIsResponse)
951{
952 static const struct pldm_msg_hdr req = {
953 .instance_id = 0,
954 .reserved = 0,
955 .datagram = 0,
956 .request = 0,
957 .type = 0,
958 .header_ver = 1,
959 .command = 0x01,
960 };
961 static const struct pldm_msg_hdr resp = {
962 .instance_id = 0,
963 .reserved = 0,
964 .datagram = 0,
965 .request = 0,
966 .type = 0,
967 .header_ver = 1,
968 .command = 0x02,
969 };
970
971 ASSERT_EQ(pldm_msg_hdr_correlate_response(&req, &resp), false);
972}
973#endif