1*d6a95748SAlexander Hansen #include <bitset>
2*d6a95748SAlexander Hansen #include <cstdint>
3*d6a95748SAlexander Hansen #include <libpldm/firmware_update.h>
4*d6a95748SAlexander Hansen #include <libpldm++/types.hpp>
5*d6a95748SAlexander Hansen #include <libpldm++/firmware_update.hpp>
6*d6a95748SAlexander Hansen #include <map>
7*d6a95748SAlexander Hansen #include <string>
8*d6a95748SAlexander Hansen #include <vector>
9*d6a95748SAlexander Hansen #include <optional>
10*d6a95748SAlexander Hansen #include <memory>
11*d6a95748SAlexander Hansen
DescriptorData(const struct DescriptorData & ref)12*d6a95748SAlexander Hansen pldm::fw_update::DescriptorData::DescriptorData(const struct DescriptorData &ref)
13*d6a95748SAlexander Hansen : vendorDefinedDescriptorTitle(ref.vendorDefinedDescriptorTitle),
14*d6a95748SAlexander Hansen data(ref.data)
15*d6a95748SAlexander Hansen {
16*d6a95748SAlexander Hansen }
17*d6a95748SAlexander Hansen
DescriptorData(const std::vector<uint8_t> & data)18*d6a95748SAlexander Hansen pldm::fw_update::DescriptorData::DescriptorData(const std::vector<uint8_t> &data)
19*d6a95748SAlexander Hansen : data(data)
20*d6a95748SAlexander Hansen {
21*d6a95748SAlexander Hansen }
22*d6a95748SAlexander Hansen
DescriptorData(const std::string & title,const std::vector<uint8_t> & data)23*d6a95748SAlexander Hansen pldm::fw_update::DescriptorData::DescriptorData(
24*d6a95748SAlexander Hansen const std::string &title, const std::vector<uint8_t> &data)
25*d6a95748SAlexander Hansen : vendorDefinedDescriptorTitle(title), data(data)
26*d6a95748SAlexander Hansen {
27*d6a95748SAlexander Hansen }
28*d6a95748SAlexander Hansen
29*d6a95748SAlexander Hansen LIBPLDM_ABI_TESTING
~DescriptorData()30*d6a95748SAlexander Hansen pldm::fw_update::DescriptorData::~DescriptorData()
31*d6a95748SAlexander Hansen {
32*d6a95748SAlexander Hansen }
33*d6a95748SAlexander Hansen
34*d6a95748SAlexander Hansen LIBPLDM_ABI_TESTING
operator ==(const DescriptorData & other) const35*d6a95748SAlexander Hansen bool pldm::fw_update::DescriptorData::operator==(
36*d6a95748SAlexander Hansen const DescriptorData &other) const
37*d6a95748SAlexander Hansen {
38*d6a95748SAlexander Hansen if (CompareNEQ(&DescriptorData::vendorDefinedDescriptorTitle, other)) {
39*d6a95748SAlexander Hansen return false;
40*d6a95748SAlexander Hansen }
41*d6a95748SAlexander Hansen if (CompareNEQ(&DescriptorData::data, other)) {
42*d6a95748SAlexander Hansen return false;
43*d6a95748SAlexander Hansen }
44*d6a95748SAlexander Hansen return true;
45*d6a95748SAlexander Hansen }
46*d6a95748SAlexander Hansen
ComponentImageInfo(uint16_t componentClassification,uint16_t componentIdentifier,uint32_t componentComparisonStamp,std::bitset<16> componentOptions,std::bitset<16> requestedComponentActivationMethod,const variable_field & componentLocation,const std::string & componentVersion)47*d6a95748SAlexander Hansen pldm::fw_update::ComponentImageInfo::ComponentImageInfo(
48*d6a95748SAlexander Hansen uint16_t componentClassification, uint16_t componentIdentifier,
49*d6a95748SAlexander Hansen uint32_t componentComparisonStamp, std::bitset<16> componentOptions,
50*d6a95748SAlexander Hansen std::bitset<16> requestedComponentActivationMethod,
51*d6a95748SAlexander Hansen const variable_field &componentLocation,
52*d6a95748SAlexander Hansen const std::string &componentVersion)
53*d6a95748SAlexander Hansen : componentClassification(componentClassification),
54*d6a95748SAlexander Hansen componentIdentifier(componentIdentifier),
55*d6a95748SAlexander Hansen compComparisonStamp(componentComparisonStamp),
56*d6a95748SAlexander Hansen componentOptions(componentOptions),
57*d6a95748SAlexander Hansen requestedComponentActivationMethod(
58*d6a95748SAlexander Hansen requestedComponentActivationMethod),
59*d6a95748SAlexander Hansen componentLocation(componentLocation),
60*d6a95748SAlexander Hansen componentVersion(componentVersion)
61*d6a95748SAlexander Hansen {
62*d6a95748SAlexander Hansen }
63*d6a95748SAlexander Hansen
64*d6a95748SAlexander Hansen LIBPLDM_ABI_TESTING
ComponentImageInfo(const ComponentImageInfo & ref)65*d6a95748SAlexander Hansen pldm::fw_update::ComponentImageInfo::ComponentImageInfo(
66*d6a95748SAlexander Hansen const ComponentImageInfo &ref)
67*d6a95748SAlexander Hansen : componentClassification(ref.componentClassification),
68*d6a95748SAlexander Hansen componentIdentifier(ref.componentIdentifier),
69*d6a95748SAlexander Hansen compComparisonStamp(ref.compComparisonStamp),
70*d6a95748SAlexander Hansen componentOptions(ref.componentOptions),
71*d6a95748SAlexander Hansen requestedComponentActivationMethod(
72*d6a95748SAlexander Hansen ref.requestedComponentActivationMethod),
73*d6a95748SAlexander Hansen componentLocation(ref.componentLocation),
74*d6a95748SAlexander Hansen componentVersion(ref.componentVersion)
75*d6a95748SAlexander Hansen {
76*d6a95748SAlexander Hansen }
77*d6a95748SAlexander Hansen
78*d6a95748SAlexander Hansen LIBPLDM_ABI_TESTING
operator ==(const ComponentImageInfo & other) const79*d6a95748SAlexander Hansen bool pldm::fw_update::ComponentImageInfo::operator==(
80*d6a95748SAlexander Hansen const ComponentImageInfo &other) const
81*d6a95748SAlexander Hansen {
82*d6a95748SAlexander Hansen if (CompareNEQ(&ComponentImageInfo::componentClassification, other)) {
83*d6a95748SAlexander Hansen return false;
84*d6a95748SAlexander Hansen }
85*d6a95748SAlexander Hansen if (CompareNEQ(&ComponentImageInfo::componentIdentifier, other)) {
86*d6a95748SAlexander Hansen return false;
87*d6a95748SAlexander Hansen }
88*d6a95748SAlexander Hansen if (CompareNEQ(&ComponentImageInfo::compComparisonStamp, other)) {
89*d6a95748SAlexander Hansen return false;
90*d6a95748SAlexander Hansen }
91*d6a95748SAlexander Hansen if (CompareNEQ(&ComponentImageInfo::componentOptions, other)) {
92*d6a95748SAlexander Hansen return false;
93*d6a95748SAlexander Hansen }
94*d6a95748SAlexander Hansen if (CompareNEQ(&ComponentImageInfo::requestedComponentActivationMethod,
95*d6a95748SAlexander Hansen other)) {
96*d6a95748SAlexander Hansen return false;
97*d6a95748SAlexander Hansen }
98*d6a95748SAlexander Hansen if (HasMember(&ComponentImageInfo::componentLocation) &&
99*d6a95748SAlexander Hansen other.HasMember(&ComponentImageInfo::componentLocation)) {
100*d6a95748SAlexander Hansen if (componentLocation.length !=
101*d6a95748SAlexander Hansen other.componentLocation.length) {
102*d6a95748SAlexander Hansen return false;
103*d6a95748SAlexander Hansen }
104*d6a95748SAlexander Hansen }
105*d6a95748SAlexander Hansen if (CompareNEQ(&ComponentImageInfo::componentVersion, other)) {
106*d6a95748SAlexander Hansen return false;
107*d6a95748SAlexander Hansen }
108*d6a95748SAlexander Hansen return true;
109*d6a95748SAlexander Hansen }
110*d6a95748SAlexander Hansen
111*d6a95748SAlexander Hansen LIBPLDM_ABI_TESTING
~ComponentImageInfo()112*d6a95748SAlexander Hansen pldm::fw_update::ComponentImageInfo::~ComponentImageInfo()
113*d6a95748SAlexander Hansen {
114*d6a95748SAlexander Hansen }
115*d6a95748SAlexander Hansen
FirmwareDeviceIDRecord(const std::bitset<32> & deviceUpdateOptionFlags,const std::vector<size_t> & applicableComponents,const std::string & componentImageSetVersion,const std::map<uint16_t,std::unique_ptr<DescriptorData>> & descriptorsIn,const std::vector<uint8_t> & firmwareDevicePackageData)116*d6a95748SAlexander Hansen pldm::fw_update::FirmwareDeviceIDRecord::FirmwareDeviceIDRecord(
117*d6a95748SAlexander Hansen const std::bitset<32> &deviceUpdateOptionFlags,
118*d6a95748SAlexander Hansen const std::vector<size_t> &applicableComponents,
119*d6a95748SAlexander Hansen const std::string &componentImageSetVersion,
120*d6a95748SAlexander Hansen const std::map<uint16_t, std::unique_ptr<DescriptorData> >
121*d6a95748SAlexander Hansen &descriptorsIn,
122*d6a95748SAlexander Hansen const std::vector<uint8_t> &firmwareDevicePackageData)
123*d6a95748SAlexander Hansen : deviceUpdateOptionFlags(deviceUpdateOptionFlags),
124*d6a95748SAlexander Hansen applicableComponents(applicableComponents),
125*d6a95748SAlexander Hansen componentImageSetVersionString(componentImageSetVersion),
126*d6a95748SAlexander Hansen recordDescriptors([&descriptorsIn]() {
127*d6a95748SAlexander Hansen std::map<uint16_t, std::unique_ptr<DescriptorData> > res;
128*d6a95748SAlexander Hansen // We have to init the map here manually since the descriptor constructor
129*d6a95748SAlexander Hansen // is not a friend of the template which would otherwise be able to construct it.
130*d6a95748SAlexander Hansen for (const auto &[key, desc] : descriptorsIn) {
131*d6a95748SAlexander Hansen res[key] = std::unique_ptr<DescriptorData>(
132*d6a95748SAlexander Hansen new DescriptorData(*desc));
133*d6a95748SAlexander Hansen }
134*d6a95748SAlexander Hansen
135*d6a95748SAlexander Hansen return res;
136*d6a95748SAlexander Hansen }()),
137*d6a95748SAlexander Hansen firmwareDevicePackageData(firmwareDevicePackageData)
138*d6a95748SAlexander Hansen {
139*d6a95748SAlexander Hansen }
140*d6a95748SAlexander Hansen
141*d6a95748SAlexander Hansen LIBPLDM_ABI_TESTING
FirmwareDeviceIDRecord(const FirmwareDeviceIDRecord & ref)142*d6a95748SAlexander Hansen pldm::fw_update::FirmwareDeviceIDRecord::FirmwareDeviceIDRecord(
143*d6a95748SAlexander Hansen const FirmwareDeviceIDRecord &ref)
144*d6a95748SAlexander Hansen : deviceUpdateOptionFlags(ref.deviceUpdateOptionFlags),
145*d6a95748SAlexander Hansen applicableComponents(ref.applicableComponents),
146*d6a95748SAlexander Hansen componentImageSetVersionString(ref.componentImageSetVersionString),
147*d6a95748SAlexander Hansen recordDescriptors([&ref]() {
148*d6a95748SAlexander Hansen std::map<uint16_t, std::unique_ptr<DescriptorData> > res;
149*d6a95748SAlexander Hansen // We have to init the map here manually since the descriptor constructor
150*d6a95748SAlexander Hansen // is not a friend of the template which would otherwise be able to construct it.
151*d6a95748SAlexander Hansen for (const auto &[key, desc] : ref.recordDescriptors) {
152*d6a95748SAlexander Hansen res[key] = std::unique_ptr<DescriptorData>(
153*d6a95748SAlexander Hansen new DescriptorData(*desc));
154*d6a95748SAlexander Hansen }
155*d6a95748SAlexander Hansen
156*d6a95748SAlexander Hansen return res;
157*d6a95748SAlexander Hansen }()),
158*d6a95748SAlexander Hansen firmwareDevicePackageData(ref.firmwareDevicePackageData)
159*d6a95748SAlexander Hansen {
160*d6a95748SAlexander Hansen }
161*d6a95748SAlexander Hansen
162*d6a95748SAlexander Hansen LIBPLDM_ABI_TESTING
~FirmwareDeviceIDRecord()163*d6a95748SAlexander Hansen pldm::fw_update::FirmwareDeviceIDRecord::~FirmwareDeviceIDRecord()
164*d6a95748SAlexander Hansen {
165*d6a95748SAlexander Hansen }
166*d6a95748SAlexander Hansen
167*d6a95748SAlexander Hansen LIBPLDM_ABI_TESTING
168*d6a95748SAlexander Hansen const std::vector<uint16_t>
getDescriptorTypes() const169*d6a95748SAlexander Hansen pldm::fw_update::FirmwareDeviceIDRecord::getDescriptorTypes() const
170*d6a95748SAlexander Hansen {
171*d6a95748SAlexander Hansen std::vector<uint16_t> res;
172*d6a95748SAlexander Hansen res.reserve(recordDescriptors.size());
173*d6a95748SAlexander Hansen
174*d6a95748SAlexander Hansen for (auto &[k, _] : recordDescriptors) {
175*d6a95748SAlexander Hansen res.emplace_back(k);
176*d6a95748SAlexander Hansen }
177*d6a95748SAlexander Hansen return res;
178*d6a95748SAlexander Hansen }
179*d6a95748SAlexander Hansen
180*d6a95748SAlexander Hansen LIBPLDM_ABI_TESTING
operator ==(const FirmwareDeviceIDRecord & other) const181*d6a95748SAlexander Hansen bool pldm::fw_update::FirmwareDeviceIDRecord::operator==(
182*d6a95748SAlexander Hansen const FirmwareDeviceIDRecord &other) const
183*d6a95748SAlexander Hansen {
184*d6a95748SAlexander Hansen if (CompareNEQ(&FirmwareDeviceIDRecord::deviceUpdateOptionFlags,
185*d6a95748SAlexander Hansen other)) {
186*d6a95748SAlexander Hansen return false;
187*d6a95748SAlexander Hansen }
188*d6a95748SAlexander Hansen if (CompareNEQ(&FirmwareDeviceIDRecord::applicableComponents, other)) {
189*d6a95748SAlexander Hansen return false;
190*d6a95748SAlexander Hansen }
191*d6a95748SAlexander Hansen if (CompareNEQ(&FirmwareDeviceIDRecord::componentImageSetVersionString,
192*d6a95748SAlexander Hansen other)) {
193*d6a95748SAlexander Hansen return false;
194*d6a95748SAlexander Hansen }
195*d6a95748SAlexander Hansen if (CompareNEQ(&FirmwareDeviceIDRecord::firmwareDevicePackageData,
196*d6a95748SAlexander Hansen other)) {
197*d6a95748SAlexander Hansen return false;
198*d6a95748SAlexander Hansen }
199*d6a95748SAlexander Hansen
200*d6a95748SAlexander Hansen // need to manually compare the map since otherwise unique_ptr
201*d6a95748SAlexander Hansen // default comparison would only compare pointer values
202*d6a95748SAlexander Hansen if (HasMember(&FirmwareDeviceIDRecord::recordDescriptors) !=
203*d6a95748SAlexander Hansen other.HasMember(&FirmwareDeviceIDRecord::recordDescriptors)) {
204*d6a95748SAlexander Hansen // different size structs compare not equal
205*d6a95748SAlexander Hansen return false;
206*d6a95748SAlexander Hansen }
207*d6a95748SAlexander Hansen if (!HasMember(&FirmwareDeviceIDRecord::recordDescriptors) &&
208*d6a95748SAlexander Hansen !other.HasMember(&FirmwareDeviceIDRecord::recordDescriptors)) {
209*d6a95748SAlexander Hansen // none of them has record descriptors field
210*d6a95748SAlexander Hansen return true;
211*d6a95748SAlexander Hansen }
212*d6a95748SAlexander Hansen
213*d6a95748SAlexander Hansen // both have record descriptors field
214*d6a95748SAlexander Hansen if (recordDescriptors.size() != other.recordDescriptors.size()) {
215*d6a95748SAlexander Hansen return false;
216*d6a95748SAlexander Hansen }
217*d6a95748SAlexander Hansen
218*d6a95748SAlexander Hansen for (const auto &[k, v] : recordDescriptors) {
219*d6a95748SAlexander Hansen if (!other.recordDescriptors.contains(k)) {
220*d6a95748SAlexander Hansen return false;
221*d6a95748SAlexander Hansen }
222*d6a95748SAlexander Hansen const auto &otherDesc = other.recordDescriptors.at(k);
223*d6a95748SAlexander Hansen
224*d6a95748SAlexander Hansen if (!v.get() && !otherDesc.get()) {
225*d6a95748SAlexander Hansen continue;
226*d6a95748SAlexander Hansen }
227*d6a95748SAlexander Hansen if (!v.get() || !otherDesc.get()) {
228*d6a95748SAlexander Hansen return false;
229*d6a95748SAlexander Hansen }
230*d6a95748SAlexander Hansen
231*d6a95748SAlexander Hansen // descriptor value comparison
232*d6a95748SAlexander Hansen if (*v != *otherDesc) {
233*d6a95748SAlexander Hansen return false;
234*d6a95748SAlexander Hansen }
235*d6a95748SAlexander Hansen }
236*d6a95748SAlexander Hansen
237*d6a95748SAlexander Hansen return true;
238*d6a95748SAlexander Hansen }
239*d6a95748SAlexander Hansen
Package(const std::vector<FirmwareDeviceIDRecord> & firmwareDeviceIdRecords,const std::vector<ComponentImageInfo> & componentImageInformation)240*d6a95748SAlexander Hansen pldm::fw_update::Package::Package(
241*d6a95748SAlexander Hansen const std::vector<FirmwareDeviceIDRecord> &firmwareDeviceIdRecords,
242*d6a95748SAlexander Hansen const std::vector<ComponentImageInfo> &componentImageInformation)
243*d6a95748SAlexander Hansen : firmwareDeviceIdRecords(firmwareDeviceIdRecords),
244*d6a95748SAlexander Hansen componentImageInformation(componentImageInformation)
245*d6a95748SAlexander Hansen {
246*d6a95748SAlexander Hansen }
247*d6a95748SAlexander Hansen
248*d6a95748SAlexander Hansen LIBPLDM_ABI_TESTING
Package(const Package & ref)249*d6a95748SAlexander Hansen pldm::fw_update::Package::Package(const Package &ref)
250*d6a95748SAlexander Hansen : firmwareDeviceIdRecords(ref.firmwareDeviceIdRecords),
251*d6a95748SAlexander Hansen componentImageInformation(ref.componentImageInformation)
252*d6a95748SAlexander Hansen {
253*d6a95748SAlexander Hansen }
254*d6a95748SAlexander Hansen
255*d6a95748SAlexander Hansen LIBPLDM_ABI_TESTING
~Package()256*d6a95748SAlexander Hansen pldm::fw_update::Package::~Package()
257*d6a95748SAlexander Hansen {
258*d6a95748SAlexander Hansen }
259*d6a95748SAlexander Hansen
260*d6a95748SAlexander Hansen LIBPLDM_ABI_TESTING
operator ==(const Package & other) const261*d6a95748SAlexander Hansen bool pldm::fw_update::Package::operator==(const Package &other) const
262*d6a95748SAlexander Hansen {
263*d6a95748SAlexander Hansen if (CompareNEQ(&Package::firmwareDeviceIdRecords, other)) {
264*d6a95748SAlexander Hansen return false;
265*d6a95748SAlexander Hansen }
266*d6a95748SAlexander Hansen if (CompareNEQ(&Package::componentImageInformation, other)) {
267*d6a95748SAlexander Hansen return false;
268*d6a95748SAlexander Hansen }
269*d6a95748SAlexander Hansen return true;
270*d6a95748SAlexander Hansen }
271