blob: f4f0ec1e6bf7e0ea580b246fe9076451c62fe9f1 [file] [log] [blame]
Gilbert Chen6c7fed42022-02-22 15:40:17 +00001#include "libpldm/base.h"
2#include "libpldm/bios.h"
3#include "libpldm/fru.h"
4#include "libpldm/platform.h"
5
6#include "common/instance_id.hpp"
7#include "common/types.hpp"
8#include "mock_terminus_manager.hpp"
Thu Nguyen38e12aa2025-01-21 22:47:56 +00009#include "platform-mc/platform_manager.hpp"
Gilbert Chen6c7fed42022-02-22 15:40:17 +000010#include "platform-mc/terminus_manager.hpp"
11#include "requester/handler.hpp"
12#include "requester/mctp_endpoint_discovery.hpp"
13#include "requester/request.hpp"
14#include "test/test_instance_id.hpp"
15
16#include <sdbusplus/timer.hpp>
17#include <sdeventplus/event.hpp>
18
19#include <gmock/gmock.h>
20#include <gtest/gtest.h>
21
22using ::testing::AtLeast;
23using ::testing::Between;
24using ::testing::Exactly;
25using ::testing::NiceMock;
26using ::testing::Return;
27
28class TerminusManagerTest : public testing::Test
29{
30 protected:
31 TerminusManagerTest() :
32 bus(pldm::utils::DBusHandler::getBus()),
33 event(sdeventplus::Event::get_default()), instanceIdDb(),
34 reqHandler(pldmTransport, event, instanceIdDb, false,
35 std::chrono::seconds(1), 2, std::chrono::milliseconds(100)),
Thu Nguyen51d66b52024-08-06 09:15:55 +000036 terminusManager(event, reqHandler, instanceIdDb, termini, nullptr,
37 pldm::BmcMctpEid),
Thu Nguyen38e12aa2025-01-21 22:47:56 +000038 mockTerminusManager(event, reqHandler, instanceIdDb, termini, nullptr),
39 platformManager(mockTerminusManager, termini, nullptr)
Gilbert Chen6c7fed42022-02-22 15:40:17 +000040 {}
41
42 PldmTransport* pldmTransport = nullptr;
43 sdbusplus::bus_t& bus;
44 sdeventplus::Event event;
45 TestInstanceIdDb instanceIdDb;
46 pldm::requester::Handler<pldm::requester::Request> reqHandler;
47 pldm::platform_mc::TerminusManager terminusManager;
48 pldm::platform_mc::MockTerminusManager mockTerminusManager;
Thu Nguyen38e12aa2025-01-21 22:47:56 +000049 pldm::platform_mc::PlatformManager platformManager;
Gilbert Chen6c7fed42022-02-22 15:40:17 +000050 std::map<pldm_tid_t, std::shared_ptr<pldm::platform_mc::Terminus>> termini;
51};
52
53TEST_F(TerminusManagerTest, mapTidTest)
54{
55 pldm::MctpInfo mctpInfo1(8, "", "", 0);
56
57 auto mappedTid1 = terminusManager.mapTid(mctpInfo1);
58 EXPECT_NE(mappedTid1, std::nullopt);
59
60 auto tid1 = terminusManager.toTid(mctpInfo1);
61 EXPECT_NE(tid1, std::nullopt);
62
63 auto mctpInfo2 = terminusManager.toMctpInfo(tid1.value());
64 EXPECT_EQ(mctpInfo1, mctpInfo2.value());
65
66 auto ret = terminusManager.unmapTid(tid1.value());
67 EXPECT_EQ(ret, true);
68
69 tid1 = terminusManager.toTid(mctpInfo1);
70 EXPECT_EQ(tid1, std::nullopt);
71}
72
73TEST_F(TerminusManagerTest, negativeMapTidTest)
74{
75 // map null EID(0) to TID
76 pldm::MctpInfo m0(0, "", "", 0);
77 auto mappedTid = terminusManager.mapTid(m0);
78 EXPECT_EQ(mappedTid, std::nullopt);
79
80 // map broadcast EID(0xff) to TID
81 pldm::MctpInfo m1(0xff, "", "", 0);
82 mappedTid = terminusManager.mapTid(m1);
83 EXPECT_EQ(mappedTid, std::nullopt);
84
85 // map EID to tid which has been assigned
86 pldm::MctpInfo m2(9, "", "", 1);
87 pldm::MctpInfo m3(10, "", "", 1);
88 auto mappedTid2 = terminusManager.mapTid(m2);
89 auto mappedTid3 = terminusManager.storeTerminusInfo(m3, mappedTid2.value());
90 EXPECT_NE(mappedTid2, std::nullopt);
91 EXPECT_EQ(mappedTid3, std::nullopt);
92
93 // map two mctpInfo with same EID but different network Id
94 pldm::MctpInfo m4(12, "", "", 1);
95 pldm::MctpInfo m5(12, "", "", 2);
96 auto mappedTid4 = terminusManager.mapTid(m4);
97 auto mappedTid5 = terminusManager.mapTid(m5);
98 EXPECT_NE(mappedTid4.value(), mappedTid5.value());
99
100 // map same mctpInfo twice
101 pldm::MctpInfo m6(12, "", "", 3);
102 auto mappedTid6 = terminusManager.mapTid(m6);
103 auto mappedTid6_1 = terminusManager.mapTid(m6);
104 EXPECT_EQ(mappedTid6.value(), mappedTid6_1.value());
105
106 // look up an unmapped MctpInfo to TID
107 pldm::MctpInfo m7(1, "", "", 0);
108 auto mappedTid7 = terminusManager.toTid(m7);
109 EXPECT_EQ(mappedTid7, std::nullopt);
110
111 // look up reserved TID(0)
112 auto mappedEid = terminusManager.toMctpInfo(0);
113 EXPECT_EQ(mappedEid, std::nullopt);
114
115 // look up reserved TID(0xff)
116 mappedEid = terminusManager.toMctpInfo(0xff);
117 EXPECT_EQ(mappedEid, std::nullopt);
118
119 // look up an unmapped TID
120 terminusManager.unmapTid(1);
121 mappedEid = terminusManager.toMctpInfo(1);
122 EXPECT_EQ(mappedEid, std::nullopt);
123
124 // unmap reserved TID(0)
125 auto ret = terminusManager.unmapTid(0);
126 EXPECT_EQ(ret, false);
127
128 // unmap reserved TID(0)
129 ret = terminusManager.unmapTid(0xff);
130 EXPECT_EQ(ret, false);
131}
132
133TEST_F(TerminusManagerTest, discoverMctpTerminusTest)
134{
135 const size_t getTidRespLen = PLDM_GET_TID_RESP_BYTES;
136 const size_t setTidRespLen = PLDM_SET_TID_RESP_BYTES;
137 const size_t getPldmTypesRespLen = PLDM_GET_TYPES_RESP_BYTES;
138
139 // 0.discover a mctp list
140 auto rc = mockTerminusManager.clearQueuedResponses();
141 EXPECT_EQ(rc, PLDM_SUCCESS);
142
143 std::array<uint8_t, sizeof(pldm_msg_hdr) + getTidRespLen> getTidResp0{
144 0x00, 0x02, 0x02, 0x00, 0x00};
Thu Nguyen98831af2024-07-30 09:51:00 +0000145 rc = mockTerminusManager.enqueueResponse(
146 reinterpret_cast<pldm_msg*>(getTidResp0.data()), sizeof(getTidResp0));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000147 EXPECT_EQ(rc, PLDM_SUCCESS);
148 std::array<uint8_t, sizeof(pldm_msg_hdr) + setTidRespLen> setTidResp0{
149 0x00, 0x02, 0x01, 0x00};
Thu Nguyen98831af2024-07-30 09:51:00 +0000150 rc = mockTerminusManager.enqueueResponse(
151 reinterpret_cast<pldm_msg*>(setTidResp0.data()), sizeof(setTidResp0));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000152 EXPECT_EQ(rc, PLDM_SUCCESS);
153 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPldmTypesRespLen>
154 getPldmTypesResp0{0x00, 0x02, 0x04, 0x00, 0x01, 0x00,
155 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
156 rc = mockTerminusManager.enqueueResponse(
Thu Nguyen98831af2024-07-30 09:51:00 +0000157 reinterpret_cast<pldm_msg*>(getPldmTypesResp0.data()),
158 sizeof(getPldmTypesResp0));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000159 EXPECT_EQ(rc, PLDM_SUCCESS);
160
161 pldm::MctpInfos mctpInfos{};
162 mctpInfos.emplace_back(pldm::MctpInfo(12, "", "", 1));
163 mockTerminusManager.discoverMctpTerminus(mctpInfos);
164 EXPECT_EQ(1, termini.size());
165
166 // 1.discover the same mctp list again
167 rc = mockTerminusManager.clearQueuedResponses();
168 EXPECT_EQ(rc, PLDM_SUCCESS);
169
170 std::array<uint8_t, sizeof(pldm_msg_hdr) + getTidRespLen> getTidResp1{
171 0x00, 0x02, 0x02, 0x00, 0x01};
Thu Nguyen98831af2024-07-30 09:51:00 +0000172 rc = mockTerminusManager.enqueueResponse(
173 reinterpret_cast<pldm_msg*>(getTidResp1.data()), sizeof(getTidResp1));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000174 EXPECT_EQ(rc, PLDM_SUCCESS);
175 rc = mockTerminusManager.enqueueResponse(
Thu Nguyen98831af2024-07-30 09:51:00 +0000176 reinterpret_cast<pldm_msg*>(setTidResp0.data()), sizeof(setTidResp0));
177 EXPECT_EQ(rc, PLDM_SUCCESS);
178 rc = mockTerminusManager.enqueueResponse(
179 reinterpret_cast<pldm_msg*>(getPldmTypesResp0.data()),
180 sizeof(getPldmTypesResp0));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000181 EXPECT_EQ(rc, PLDM_SUCCESS);
182
183 mockTerminusManager.discoverMctpTerminus(mctpInfos);
184 EXPECT_EQ(1, termini.size());
185
186 // 2.discover an empty mctp list
187 rc = mockTerminusManager.clearQueuedResponses();
188 EXPECT_EQ(rc, PLDM_SUCCESS);
189
190 mockTerminusManager.removeMctpTerminus(mctpInfos);
191 EXPECT_EQ(0, termini.size());
192}
193
194TEST_F(TerminusManagerTest, negativeDiscoverMctpTerminusTest)
195{
196 const size_t getTidRespLen = PLDM_GET_TID_RESP_BYTES;
197 const size_t setTidRespLen = PLDM_SET_TID_RESP_BYTES;
198 const size_t getPldmTypesRespLen = PLDM_GET_TYPES_RESP_BYTES;
199
200 // 0.terminus returns reserved tid
201 std::array<uint8_t, sizeof(pldm_msg_hdr) + getTidRespLen> getTidResp0{
202 0x00, 0x02, 0x02, 0x00, PLDM_TID_RESERVED};
Thu Nguyen98831af2024-07-30 09:51:00 +0000203 auto rc = mockTerminusManager.enqueueResponse(
204 reinterpret_cast<pldm_msg*>(getTidResp0.data()), sizeof(getTidResp0));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000205 EXPECT_EQ(rc, PLDM_SUCCESS);
206
207 pldm::MctpInfos mctpInfos{};
208 mctpInfos.emplace_back(pldm::MctpInfo(12, "", "", 1));
209 mockTerminusManager.discoverMctpTerminus(mctpInfos);
210 EXPECT_EQ(0, termini.size());
211
212 // 1.terminus return cc=pldm_error for set tid
213 std::array<uint8_t, sizeof(pldm_msg_hdr) + getTidRespLen> getTidResp1{
214 0x00, 0x02, 0x02, 0x00, 0x00};
215 std::array<uint8_t, sizeof(pldm_msg_hdr) + setTidRespLen> setTidResp1{
216 0x00, 0x02, 0x01, PLDM_ERROR};
217
Thu Nguyen98831af2024-07-30 09:51:00 +0000218 rc = mockTerminusManager.enqueueResponse(
219 reinterpret_cast<pldm_msg*>(getTidResp1.data()), sizeof(getTidResp1));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000220 EXPECT_EQ(rc, PLDM_SUCCESS);
Thu Nguyen98831af2024-07-30 09:51:00 +0000221 rc = mockTerminusManager.enqueueResponse(
222 reinterpret_cast<pldm_msg*>(setTidResp1.data()), sizeof(setTidResp1));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000223 EXPECT_EQ(rc, PLDM_SUCCESS);
224 mockTerminusManager.removeMctpTerminus(mctpInfos);
225 EXPECT_EQ(0, termini.size());
226
227 // 2.terminus return cc=unsupported_pldm_cmd for set tid cmd and return
228 // cc=pldm_error for get pldm types cmd
229 std::array<uint8_t, sizeof(pldm_msg_hdr) + getTidRespLen> getTidResp2{
230 0x00, 0x02, 0x02, 0x00, 0x00};
231 std::array<uint8_t, sizeof(pldm_msg_hdr) + setTidRespLen> setTidResp2{
232 0x00, 0x02, 0x01, PLDM_ERROR_UNSUPPORTED_PLDM_CMD};
233 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPldmTypesRespLen>
234 getPldmTypesResp2{0x00, 0x02, 0x04, PLDM_ERROR, 0x01, 0x00,
235 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
Thu Nguyen98831af2024-07-30 09:51:00 +0000236 rc = mockTerminusManager.enqueueResponse(
237 reinterpret_cast<pldm_msg*>(getTidResp2.data()), sizeof(getTidResp2));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000238 EXPECT_EQ(rc, PLDM_SUCCESS);
Thu Nguyen98831af2024-07-30 09:51:00 +0000239 rc = mockTerminusManager.enqueueResponse(
240 reinterpret_cast<pldm_msg*>(setTidResp2.data()), sizeof(setTidResp2));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000241 EXPECT_EQ(rc, PLDM_SUCCESS);
242
243 rc = mockTerminusManager.enqueueResponse(
Thu Nguyen98831af2024-07-30 09:51:00 +0000244 reinterpret_cast<pldm_msg*>(getPldmTypesResp2.data()),
245 sizeof(getPldmTypesResp2));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000246 EXPECT_EQ(rc, PLDM_SUCCESS);
247 mockTerminusManager.removeMctpTerminus(mctpInfos);
248 EXPECT_EQ(0, termini.size());
249}
250
251TEST_F(TerminusManagerTest, doesSupportTypeTest)
252{
253 const size_t getTidRespLen = PLDM_GET_TID_RESP_BYTES;
254 const size_t setTidRespLen = PLDM_SET_TID_RESP_BYTES;
255 const size_t getPldmTypesRespLen = PLDM_GET_TYPES_RESP_BYTES;
256
257 // 0.discover a mctp list
258 auto rc = mockTerminusManager.clearQueuedResponses();
259 EXPECT_EQ(rc, PLDM_SUCCESS);
260
261 std::array<uint8_t, sizeof(pldm_msg_hdr) + getTidRespLen> getTidResp0{
262 0x00, 0x02, 0x02, 0x00, 0x00};
Thu Nguyen98831af2024-07-30 09:51:00 +0000263 rc = mockTerminusManager.enqueueResponse(
264 reinterpret_cast<pldm_msg*>(getTidResp0.data()), sizeof(getTidResp0));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000265 EXPECT_EQ(rc, PLDM_SUCCESS);
266
267 std::array<uint8_t, sizeof(pldm_msg_hdr) + setTidRespLen> setTidResp0{
268 0x00, 0x02, 0x01, 0x00};
Thu Nguyen98831af2024-07-30 09:51:00 +0000269 rc = mockTerminusManager.enqueueResponse(
270 reinterpret_cast<pldm_msg*>(setTidResp0.data()), sizeof(setTidResp0));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000271 EXPECT_EQ(rc, PLDM_SUCCESS);
272
Patrick Williams16c2a0a2024-08-16 15:20:59 -0400273 uint8_t supportedType1Byte =
274 (1 << (PLDM_BASE % 8)) + (1 << (PLDM_PLATFORM % 8)) +
275 (1 << (PLDM_BIOS % 8)) + (1 << (PLDM_FRU % 8));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000276 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPldmTypesRespLen>
277 getPldmTypesResp0{0x00, 0x02, 0x04, 0x00, supportedType1Byte,
278 0x00, 0x00, 0x00, 0x00, 0x00,
279 0x00, 0x00};
280 rc = mockTerminusManager.enqueueResponse(
Thu Nguyen98831af2024-07-30 09:51:00 +0000281 reinterpret_cast<pldm_msg*>(getPldmTypesResp0.data()),
282 sizeof(getPldmTypesResp0));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000283 EXPECT_EQ(rc, PLDM_SUCCESS);
284
285 pldm::MctpInfos mctpInfos{};
286 mctpInfos.emplace_back(pldm::MctpInfo(12, "", "", 1));
287 mockTerminusManager.discoverMctpTerminus(mctpInfos);
288 EXPECT_EQ(1, termini.size());
289
290 EXPECT_EQ(true, termini.contains(1));
291 EXPECT_EQ(false, termini.contains(0));
292 EXPECT_EQ(false, termini.contains(2));
293
294 EXPECT_EQ(true, termini[1]->doesSupportType(PLDM_BASE));
295 EXPECT_EQ(true, termini[1]->doesSupportType(PLDM_PLATFORM));
296 EXPECT_EQ(true, termini[1]->doesSupportType(PLDM_BIOS));
297 EXPECT_EQ(true, termini[1]->doesSupportType(PLDM_FRU));
298 EXPECT_EQ(false, termini[1]->doesSupportType(PLDM_FWUP));
299 EXPECT_EQ(false, termini[1]->doesSupportType(PLDM_OEM));
300}
301
302TEST_F(TerminusManagerTest, doesSupportCommandTest)
303{
304 const size_t getTidRespLen = PLDM_GET_TID_RESP_BYTES;
305 const size_t setTidRespLen = PLDM_SET_TID_RESP_BYTES;
306 const size_t getPldmTypesRespLen = PLDM_GET_TYPES_RESP_BYTES;
307 const size_t getPldmCommandRespLen = PLDM_GET_COMMANDS_RESP_BYTES;
Thu Nguyen6e615622024-06-22 02:10:34 +0000308 /* PLDM_GET_VERSION_RESP_BYTES does not include 4 bytes check sum */
309 const size_t getPldmVersionRespLen =
310 PLDM_GET_VERSION_RESP_BYTES + sizeof(uint32_t);
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000311
312 // 0.discover a mctp list
313 auto rc = mockTerminusManager.clearQueuedResponses();
314 EXPECT_EQ(rc, PLDM_SUCCESS);
315
316 std::array<uint8_t, sizeof(pldm_msg_hdr) + getTidRespLen> getTidResp0{
317 0x00, 0x02, 0x02, 0x00, 0x00};
Thu Nguyen98831af2024-07-30 09:51:00 +0000318 rc = mockTerminusManager.enqueueResponse(
319 reinterpret_cast<pldm_msg*>(getTidResp0.data()), sizeof(getTidResp0));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000320 EXPECT_EQ(rc, PLDM_SUCCESS);
321
322 std::array<uint8_t, sizeof(pldm_msg_hdr) + setTidRespLen> setTidResp0{
323 0x00, 0x02, 0x01, 0x00};
Thu Nguyen98831af2024-07-30 09:51:00 +0000324 rc = mockTerminusManager.enqueueResponse(
325 reinterpret_cast<pldm_msg*>(setTidResp0.data()), sizeof(setTidResp0));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000326 EXPECT_EQ(rc, PLDM_SUCCESS);
327
328 uint8_t byte0 = (1 << (PLDM_BASE % 8)) + (1 << (PLDM_PLATFORM % 8)) +
329 (1 << (PLDM_BIOS % 8)) + (1 << (PLDM_FRU % 8));
330 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPldmTypesRespLen>
331 getPldmTypesResp0{0x00, 0x02, 0x04, 0x00, byte0, 0x00,
332 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
333 rc = mockTerminusManager.enqueueResponse(
Thu Nguyen98831af2024-07-30 09:51:00 +0000334 reinterpret_cast<pldm_msg*>(getPldmTypesResp0.data()),
335 sizeof(getPldmTypesResp0));
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000336 EXPECT_EQ(rc, PLDM_SUCCESS);
337
Thu Nguyen6e615622024-06-22 02:10:34 +0000338 /* Response GetPLDMVersion BASE, CC=0 */
339 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPldmVersionRespLen>
340 getPldmVersionBaseResp0{0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
341 0x00, 0x00, 0x05, 0x00, 0xf0, 0xf1,
342 0xf1, 0xba, 0xbe, 0x9d, 0x53};
343
344 rc = mockTerminusManager.enqueueResponse(
345 (pldm_msg*)getPldmVersionBaseResp0.data(),
346 sizeof(getPldmVersionBaseResp0));
347 EXPECT_EQ(rc, PLDM_SUCCESS);
348
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000349 /* Response GetPLDMCommand BASE, CC=0,
350 * SetTID/GetTID/GetPLDMTypes/GetPLDMCommands */
351 byte0 = (1 << (PLDM_SET_TID % 8)) + (1 << (PLDM_GET_TID % 8)) +
352 (1 << (PLDM_GET_PLDM_TYPES % 8)) +
353 (1 << (PLDM_GET_PLDM_COMMANDS % 8));
354 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPldmCommandRespLen>
Patrick Williams16c2a0a2024-08-16 15:20:59 -0400355 getPldmCommandBaseResp0{
356 0x00, 0x02, 0x05, 0x00, byte0, 0x00, 0x00, 0x00, 0x00,
357 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
358 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
359 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000360 rc = mockTerminusManager.enqueueResponse(
Thu Nguyen98831af2024-07-30 09:51:00 +0000361 reinterpret_cast<pldm_msg*>(getPldmCommandBaseResp0.data()),
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000362 sizeof(getPldmCommandBaseResp0));
363 EXPECT_EQ(rc, PLDM_SUCCESS);
364
Thu Nguyen6e615622024-06-22 02:10:34 +0000365 /* Response GetPLDMVersion PLATFORM, CC=0 */
366 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPldmVersionRespLen>
367 getPldmVersionPlatformResp0{0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
368 0x00, 0x00, 0x05, 0x00, 0xf1, 0xf2,
369 0xf1, 0x4e, 0x87, 0x72, 0x79};
370
371 rc = mockTerminusManager.enqueueResponse(
372 (pldm_msg*)getPldmVersionPlatformResp0.data(),
373 sizeof(getPldmVersionPlatformResp0));
374 EXPECT_EQ(rc, PLDM_SUCCESS);
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000375 /* Response GetPLDMCommand PLATFORM, CC=0,
376 * SetEventReceiver/PlatformEventMessage/GetSensorReading/SetNumericEffecterValue/GetNumericEffecterValue/GetPDR
377 */
378 /* byte0 command from 0x00 to 0x07 */
379 byte0 = (1 << (PLDM_SET_EVENT_RECEIVER % 8)); // byte0 = 0x10
380 /* byte1 command from 0x08 to 0xf */
381 uint8_t byte1 = (1 << (PLDM_PLATFORM_EVENT_MESSAGE % 8)) +
382 (1 << (PLDM_POLL_FOR_PLATFORM_EVENT_MESSAGE % 8)) +
383 (1 << (PLDM_EVENT_MESSAGE_SUPPORTED % 8)) +
384 (1 << (PLDM_EVENT_MESSAGE_BUFFER_SIZE % 8)); // byte1 = 0x3c
385 /* byte2 command from 0x10 to 0x17 */
386 uint8_t byte2 = (1 << (PLDM_GET_SENSOR_READING % 8)); // byte2 = 0x02
387 /* byte3 command from 0x18 to 0x1f */
388 /* byte4 command from 0x20 to 0x27 */
389 uint8_t byte4 = (1 << (PLDM_GET_STATE_SENSOR_READINGS % 8)); // byte4 = 0x02
390 /* byte5 command from 0x28 to 0x2f */
391 /* byte6 command from 0x30 to 0x37 */
392 uint8_t byte6 =
393 (1 << (PLDM_SET_NUMERIC_EFFECTER_VALUE % 8)) +
394 (1 << (PLDM_GET_NUMERIC_EFFECTER_VALUE % 8)); // byte6 = 0x06
395 /* byte7 command from 0x38 to 0x3f */
396 uint8_t byte7 = (0 << (PLDM_SET_STATE_EFFECTER_STATES % 8)); // byte7 = 0
397 /* byte8 command from 0x40 to 0x47 */
398 /* byte9 command from 0x48 to 0x4f */
399 /* byte10 command from 0x50 to 0x57 */
400 uint8_t byte10 = (1 << (PLDM_GET_PDR_REPOSITORY_INFO % 8)) +
401 (1 << (PLDM_GET_PDR % 8)); // byte10 = 0x03
402 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPldmCommandRespLen>
403 getPldmCommandPlatResp0{
404 0x00, 0x02, 0x05, 0x00, byte0, byte1, byte2, 0x00, byte4,
405 0x00, byte6, byte7, 0x00, 0x00, byte10, 0x00, 0x00, 0x00,
406 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
407 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
408 rc = mockTerminusManager.enqueueResponse(
Thu Nguyen98831af2024-07-30 09:51:00 +0000409 reinterpret_cast<pldm_msg*>(getPldmCommandPlatResp0.data()),
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000410 sizeof(getPldmCommandPlatResp0));
411 EXPECT_EQ(rc, PLDM_SUCCESS);
412
Thu Nguyen6e615622024-06-22 02:10:34 +0000413 /* Response GetPLDMVersion BIOS, CC=0 */
414 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPldmVersionRespLen>
415 getPldmVersionBiosResp0{0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
416 0x00, 0x00, 0x05, 0x00, 0xf0, 0xf0,
417 0xf1, 0xfb, 0x8f, 0x86, 0x4a};
418
419 rc = mockTerminusManager.enqueueResponse(
420 (pldm_msg*)getPldmVersionBiosResp0.data(),
421 sizeof(getPldmVersionBiosResp0));
422 EXPECT_EQ(rc, PLDM_SUCCESS);
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000423 /* Response GetPLDMCommand BIOS, CC=0, GetDateTime/SetDateTime */
424 /* byte0 command from 1 to 7 */
425 byte0 = (0 << (PLDM_GET_BIOS_TABLE % 8)) +
426 (0 << (PLDM_SET_BIOS_TABLE % 8)) +
427 (0 << (PLDM_SET_BIOS_ATTRIBUTE_CURRENT_VALUE % 8));
428 /* byte1 command from 8 to 15 */
429 byte1 = (0 << (PLDM_GET_BIOS_ATTRIBUTE_CURRENT_VALUE_BY_HANDLE % 8)) +
430 (1 << (PLDM_GET_DATE_TIME % 8)) + (1 << (PLDM_SET_DATE_TIME % 8));
431 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPldmCommandRespLen>
Patrick Williams16c2a0a2024-08-16 15:20:59 -0400432 getPldmCommandBiosResp0{
433 0x00, 0x02, 0x05, 0x00, byte0, byte1, 0x00, 0x00, 0x00,
434 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
435 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
436 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000437 rc = mockTerminusManager.enqueueResponse(
Thu Nguyen98831af2024-07-30 09:51:00 +0000438 reinterpret_cast<pldm_msg*>(getPldmCommandBiosResp0.data()),
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000439 sizeof(getPldmCommandBiosResp0));
440 EXPECT_EQ(rc, PLDM_SUCCESS);
441
Thu Nguyen6e615622024-06-22 02:10:34 +0000442 /* Response GetPLDMVersion FRU, CC=0 */
443 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPldmVersionRespLen>
444 getPldmVersionFruResp0{0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
445 0x00, 0x00, 0x05, 0x00, 0xf1, 0xf0,
446 0xf1, 0xcc, 0xe5, 0x44, 0x4b};
447
448 rc = mockTerminusManager.enqueueResponse(
449 (pldm_msg*)getPldmVersionFruResp0.data(),
450 sizeof(getPldmVersionFruResp0));
451 EXPECT_EQ(rc, PLDM_SUCCESS);
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000452 /* Response GetPLDMCommand FRU, CC=0,
453 * GetFRURecordTableMetadata/GetFRURecordTable */
454 /* byte0 command from 1 to 7 */
455 byte0 = (1 << (PLDM_GET_FRU_RECORD_TABLE_METADATA % 8)) +
456 (1 << (PLDM_GET_FRU_RECORD_TABLE % 8)) +
457 (0 << (PLDM_SET_FRU_RECORD_TABLE % 8)) +
458 (0 << (PLDM_GET_FRU_RECORD_BY_OPTION % 8));
459 /* byte0 command from 8 to 15 */
460 byte1 = 0;
461 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPldmCommandRespLen>
Patrick Williams16c2a0a2024-08-16 15:20:59 -0400462 getPldmCommandFruResp0{
463 0x00, 0x02, 0x05, 0x00, byte0, 0x00, 0x00, 0x00, 0x00,
464 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
465 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
466 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000467 rc = mockTerminusManager.enqueueResponse(
Thu Nguyen98831af2024-07-30 09:51:00 +0000468 reinterpret_cast<pldm_msg*>(getPldmCommandFruResp0.data()),
Gilbert Chen6c7fed42022-02-22 15:40:17 +0000469 sizeof(getPldmCommandFruResp0));
470 EXPECT_EQ(rc, PLDM_SUCCESS);
471
472 pldm::MctpInfos mctpInfos{};
473 mctpInfos.emplace_back(pldm::MctpInfo(12, "", "", 1));
474 mockTerminusManager.discoverMctpTerminus(mctpInfos);
475 EXPECT_EQ(1, termini.size());
476 EXPECT_EQ(true, termini.contains(1));
477 EXPECT_EQ(false, termini.contains(0));
478 EXPECT_EQ(false, termini.contains(2));
479
480 EXPECT_EQ(true, termini[1]->doesSupportType(PLDM_BASE));
481 EXPECT_EQ(true, termini[1]->doesSupportType(PLDM_PLATFORM));
482 EXPECT_EQ(true, termini[1]->doesSupportType(PLDM_BIOS));
483 EXPECT_EQ(true, termini[1]->doesSupportType(PLDM_FRU));
484 /* Check PLDM Base commands */
485 EXPECT_EQ(true, termini[1]->doesSupportCommand(PLDM_BASE, PLDM_SET_TID));
486 EXPECT_EQ(true, termini[1]->doesSupportCommand(PLDM_BASE, PLDM_GET_TID));
487 EXPECT_EQ(false,
488 termini[1]->doesSupportCommand(PLDM_BASE, PLDM_GET_PLDM_VERSION));
489 EXPECT_EQ(true,
490 termini[1]->doesSupportCommand(PLDM_BASE, PLDM_GET_PLDM_TYPES));
491
492 EXPECT_EQ(true, termini[1]->doesSupportCommand(PLDM_BASE,
493 PLDM_GET_PLDM_COMMANDS));
494 EXPECT_EQ(false, termini[1]->doesSupportCommand(PLDM_BASE,
495 PLDM_MULTIPART_RECEIVE));
496
497 /* Check PLDM Platform commands */
498 EXPECT_EQ(true, termini[1]->doesSupportCommand(PLDM_PLATFORM,
499 PLDM_SET_EVENT_RECEIVER));
500 EXPECT_EQ(true, termini[1]->doesSupportCommand(
501 PLDM_PLATFORM, PLDM_PLATFORM_EVENT_MESSAGE));
502 EXPECT_EQ(true, termini[1]->doesSupportCommand(
503 PLDM_PLATFORM, PLDM_POLL_FOR_PLATFORM_EVENT_MESSAGE));
504 EXPECT_EQ(true, termini[1]->doesSupportCommand(
505 PLDM_PLATFORM, PLDM_EVENT_MESSAGE_SUPPORTED));
506 EXPECT_EQ(true, termini[1]->doesSupportCommand(
507 PLDM_PLATFORM, PLDM_EVENT_MESSAGE_BUFFER_SIZE));
508 EXPECT_EQ(true, termini[1]->doesSupportCommand(PLDM_PLATFORM,
509 PLDM_GET_SENSOR_READING));
510 EXPECT_EQ(true, termini[1]->doesSupportCommand(
511 PLDM_PLATFORM, PLDM_GET_STATE_SENSOR_READINGS));
512 EXPECT_EQ(true, termini[1]->doesSupportCommand(
513 PLDM_PLATFORM, PLDM_SET_NUMERIC_EFFECTER_VALUE));
514 EXPECT_EQ(true, termini[1]->doesSupportCommand(
515 PLDM_PLATFORM, PLDM_GET_NUMERIC_EFFECTER_VALUE));
516 EXPECT_EQ(false, termini[1]->doesSupportCommand(
517 PLDM_PLATFORM, PLDM_SET_STATE_EFFECTER_STATES));
518 EXPECT_EQ(true, termini[1]->doesSupportCommand(
519 PLDM_PLATFORM, PLDM_GET_PDR_REPOSITORY_INFO));
520 EXPECT_EQ(true,
521 termini[1]->doesSupportCommand(PLDM_PLATFORM, PLDM_GET_PDR));
522
523 /* Check PLDM Bios commands */
524 EXPECT_EQ(false,
525 termini[1]->doesSupportCommand(PLDM_BIOS, PLDM_GET_BIOS_TABLE));
526 EXPECT_EQ(false,
527 termini[1]->doesSupportCommand(PLDM_BIOS, PLDM_SET_BIOS_TABLE));
528 EXPECT_EQ(false, termini[1]->doesSupportCommand(
529 PLDM_BIOS, PLDM_SET_BIOS_ATTRIBUTE_CURRENT_VALUE));
530 EXPECT_EQ(false,
531 termini[1]->doesSupportCommand(
532 PLDM_BIOS, PLDM_GET_BIOS_ATTRIBUTE_CURRENT_VALUE_BY_HANDLE));
533 EXPECT_EQ(true,
534 termini[1]->doesSupportCommand(PLDM_BIOS, PLDM_GET_DATE_TIME));
535 EXPECT_EQ(true,
536 termini[1]->doesSupportCommand(PLDM_BIOS, PLDM_SET_DATE_TIME));
537
538 /* Check PLDM Fru commands */
539 EXPECT_EQ(true, termini[1]->doesSupportCommand(
540 PLDM_FRU, PLDM_GET_FRU_RECORD_TABLE_METADATA));
541 EXPECT_EQ(true, termini[1]->doesSupportCommand(PLDM_FRU,
542 PLDM_GET_FRU_RECORD_TABLE));
543 EXPECT_EQ(false, termini[1]->doesSupportCommand(PLDM_FRU,
544 PLDM_SET_FRU_RECORD_TABLE));
545 EXPECT_EQ(false, termini[1]->doesSupportCommand(
546 PLDM_FRU, PLDM_GET_FRU_RECORD_BY_OPTION));
547}
Thu Nguyen38e12aa2025-01-21 22:47:56 +0000548
549TEST_F(TerminusManagerTest, getActiveEidByNameTest)
550{
551 // Add terminus
552 pldm::MctpInfo mctpInfo(10, "", "", 1);
553 auto mappedTid = mockTerminusManager.mapTid(mctpInfo);
554 auto tid = mappedTid.value();
555 termini[tid] = std::make_shared<pldm::platform_mc::Terminus>(
Chaul Lyfdf61cc2025-01-22 07:55:45 +0000556 tid, 1 << PLDM_BASE | 1 << PLDM_PLATFORM, event);
Thu Nguyen38e12aa2025-01-21 22:47:56 +0000557 auto terminus = termini[tid];
558
559 auto mappedTid1 = terminusManager.mapTid(mctpInfo);
560 EXPECT_EQ(mappedTid1, mappedTid);
561
562 auto mctpInfo1 = terminusManager.toMctpInfo(tid);
563 EXPECT_EQ(mctpInfo, mctpInfo1.value());
564
565 /* Set supported command by terminus */
566 auto size = PLDM_MAX_TYPES * (PLDM_MAX_CMDS_PER_TYPE / 8);
567 std::vector<uint8_t> pldmCmds(size);
568 uint8_t type = PLDM_PLATFORM;
569 uint8_t cmd = PLDM_GET_PDR;
570 auto idx = type * (PLDM_MAX_CMDS_PER_TYPE / 8) + (cmd / 8);
571 pldmCmds[idx] = pldmCmds[idx] | (1 << (cmd % 8));
572 cmd = PLDM_GET_PDR_REPOSITORY_INFO;
573 idx = type * (PLDM_MAX_CMDS_PER_TYPE / 8) + (cmd / 8);
574 pldmCmds[idx] = pldmCmds[idx] | (1 << (cmd % 8));
575 termini[tid]->setSupportedCommands(pldmCmds);
576
577 // queue getPDRRepositoryInfo response
578 const size_t getPDRRepositoryInfoLen =
579 PLDM_GET_PDR_REPOSITORY_INFO_RESP_BYTES;
580 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPDRRepositoryInfoLen>
581 getPDRRepositoryInfoResp{
582 0x0, 0x02, 0x50, PLDM_SUCCESS,
583 0x0, // repositoryState
584 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0,
585 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // updateTime
586 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0,
587 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // OEMUpdateTime
588 2, 0x0, 0x0, 0x0, // recordCount
589 0x0, 0x1, 0x0, 0x0, // repositorySize
590 59, 0x0, 0x0, 0x0, // largestRecordSize
591 0x0 // dataTransferHandleTimeout
592 };
593 auto rc = mockTerminusManager.enqueueResponse(
594 reinterpret_cast<pldm_msg*>(getPDRRepositoryInfoResp.data()),
595 sizeof(getPDRRepositoryInfoResp));
596 EXPECT_EQ(rc, PLDM_SUCCESS);
597
598 // queue getPDR responses
599 const size_t getPdrRespLen = 81;
600 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPdrRespLen> getPdrResp{
601 0x0, 0x02, 0x51, PLDM_SUCCESS, 0x1, 0x0, 0x0, 0x0, // nextRecordHandle
602 0x0, 0x0, 0x0, 0x0, // nextDataTransferHandle
603 0x5, // transferFlag
604 69, 0x0, // responseCount
605 // numeric Sensor PDR
606 0x0, 0x0, 0x0,
607 0x0, // record handle
608 0x1, // PDRHeaderVersion
609 PLDM_NUMERIC_SENSOR_PDR, // PDRType
610 0x0,
611 0x0, // recordChangeNumber
612 PLDM_PDR_NUMERIC_SENSOR_PDR_FIXED_LENGTH +
613 PLDM_PDR_NUMERIC_SENSOR_PDR_VARIED_SENSOR_DATA_SIZE_MIN_LENGTH +
614 PLDM_PDR_NUMERIC_SENSOR_PDR_VARIED_RANGE_FIELD_MIN_LENGTH,
615 0, // dataLength
616 0,
617 0, // PLDMTerminusHandle
618 0x1,
619 0x0, // sensorID=1
620 120,
621 0, // entityType=Power Supply(120)
622 1,
623 0, // entityInstanceNumber
624 0x1,
625 0x0, // containerID=1
626 PLDM_NO_INIT, // sensorInit
627 false, // sensorAuxiliaryNamesPDR
628 PLDM_SENSOR_UNIT_DEGRESS_C, // baseUint(2)=degrees C
629 1, // unitModifier = 1
630 0, // rateUnit
631 0, // baseOEMUnitHandle
632 0, // auxUnit
633 0, // auxUnitModifier
634 0, // auxRateUnit
635 0, // rel
636 0, // auxOEMUnitHandle
637 true, // isLinear
638 PLDM_SENSOR_DATA_SIZE_UINT8, // sensorDataSize
639 0, 0, 0xc0,
640 0x3f, // resolution=1.5
641 0, 0, 0x80,
642 0x3f, // offset=1.0
643 0,
644 0, // accuracy
645 0, // plusTolerance
646 0, // minusTolerance
647 2, // hysteresis
648 0, // supportedThresholds
649 0, // thresholdAndHysteresisVolatility
650 0, 0, 0x80,
651 0x3f, // stateTransistionInterval=1.0
652 0, 0, 0x80,
653 0x3f, // updateInverval=1.0
654 255, // maxReadable
655 0, // minReadable
656 PLDM_RANGE_FIELD_FORMAT_UINT8, // rangeFieldFormat
657 0, // rangeFieldsupport
658 0, // nominalValue
659 0, // normalMax
660 0, // normalMin
661 0, // warningHigh
662 0, // warningLow
663 0, // criticalHigh
664 0, // criticalLow
665 0, // fatalHigh
666 0 // fatalLow
667 };
668 rc = mockTerminusManager.enqueueResponse(
669 reinterpret_cast<pldm_msg*>(getPdrResp.data()), sizeof(getPdrResp));
670 EXPECT_EQ(rc, PLDM_SUCCESS);
671
672 const size_t getPdrAuxNameRespLen = 39;
673 std::array<uint8_t, sizeof(pldm_msg_hdr) + getPdrAuxNameRespLen>
674 getPdrAuxNameResp{
675 0x0, 0x02, 0x51, PLDM_SUCCESS, 0x0, 0x0, 0x0,
676 0x0, // nextRecordHandle
677 0x0, 0x0, 0x0, 0x0, // nextDataTransferHandle
678 0x5, // transferFlag
679 0x1b, 0x0, // responseCount
680 // Common PDR Header
681 0x1, 0x0, 0x0,
682 0x0, // record handle
683 0x1, // PDRHeaderVersion
684 PLDM_ENTITY_AUXILIARY_NAMES_PDR, // PDRType
685 0x1,
686 0x0, // recordChangeNumber
687 0x11,
688 0, // dataLength
689 /* Entity Auxiliary Names PDR Data*/
690 3,
691 0x80, // entityType system software
692 0x1,
693 0x0, // Entity instance number =1
694 0,
695 0, // Overall system
696 0, // shared Name Count one name only
697 01, // nameStringCount
698 0x65, 0x6e, 0x00,
699 0x00, // Language Tag "en"
700 0x53, 0x00, 0x30, 0x00,
701 0x00 // Entity Name "S0"
702 };
703 rc = mockTerminusManager.enqueueResponse(
704 reinterpret_cast<pldm_msg*>(getPdrAuxNameResp.data()),
705 sizeof(getPdrAuxNameResp));
706 EXPECT_EQ(rc, PLDM_SUCCESS);
707
708 mockTerminusManager.updateMctpEndpointAvailability(mctpInfo, true);
709 terminusManager.updateMctpEndpointAvailability(mctpInfo, true);
710
711 stdexec::sync_wait(platformManager.initTerminus());
712 EXPECT_EQ(true, terminus->initialized);
713 EXPECT_EQ(2, terminus->pdrs.size());
714 EXPECT_EQ(1, termini.size());
715 EXPECT_EQ("S0", terminus->getTerminusName().value());
716 EXPECT_EQ(10, terminusManager.getActiveEidByName("S0").value());
717 EXPECT_EQ(false, terminusManager.getActiveEidByName("S1").has_value());
718}