gem5  v22.1.0.0
smbios.cc
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2008 The Hewlett-Packard Development Company
3  * All rights reserved.
4  *
5  * The license below extends only to copyright in the software and shall
6  * not be construed as granting a license to any other intellectual
7  * property including but not limited to intellectual property relating
8  * to a hardware implementation of the functionality of the software
9  * licensed hereunder. You may use the software subject to the license
10  * terms below provided that you ensure that this notice is replicated
11  * unmodified and in its entirety in all distributions of the software,
12  * modified or unmodified, in source code or in binary form.
13  *
14  * Copyright (c) 2008 The Regents of The University of Michigan
15  * All rights reserved.
16  *
17  * Redistribution and use in source and binary forms, with or without
18  * modification, are permitted provided that the following conditions are
19  * met: redistributions of source code must retain the above copyright
20  * notice, this list of conditions and the following disclaimer;
21  * redistributions in binary form must reproduce the above copyright
22  * notice, this list of conditions and the following disclaimer in the
23  * documentation and/or other materials provided with the distribution;
24  * neither the name of the copyright holders nor the names of its
25  * contributors may be used to endorse or promote products derived from
26  * this software without specific prior written permission.
27  *
28  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
29  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
30  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
31  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
32  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
33  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
34  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
35  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
36  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
37  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
38  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
39  */
40 
41 #include "arch/x86/bios/smbios.hh"
42 
43 #include "base/types.hh"
44 #include "mem/port_proxy.hh"
45 #include "params/X86SMBiosBiosInformation.hh"
46 #include "params/X86SMBiosSMBiosStructure.hh"
47 #include "params/X86SMBiosSMBiosTable.hh"
48 #include "sim/byteswap.hh"
49 
50 namespace gem5
51 {
52 
55  SMBiosHeader::formattedArea[] = {0,0,0,0,0};
62 
63 template <class T>
64 uint64_t
66 {
67  uint64_t val = 0;
68  typename T::iterator vecIt;
69  for (vecIt = vec.begin(); vecIt != vec.end(); vecIt++) {
70  val |= (1 << (*vecIt));
71  }
72  return val;
73 }
74 
75 uint16_t
77 {
78  proxy.writeBlob(addr, &type, 1);
79 
80  uint8_t length = getLength();
81  proxy.writeBlob(addr + 1, &length, 1);
82 
83  uint16_t handleGuest = htole(handle);
84  proxy.writeBlob(addr + 2, &handleGuest, 2);
85 
86  return length + getStringLength();
87 }
88 
90  const Params &p, uint8_t _type) :
91  SimObject(p), type(_type), handle(0), stringFields(false)
92 {}
93 
94 void
96  PortProxy& proxy, Addr addr)
97 {
99  Addr offset = 0;
100 
101  const uint8_t nullTerminator = 0;
102 
103  // If there are string fields but none of them are used, that's a
104  // special case which is handled by this if.
105  if (strings.size() == 0 && stringFields) {
106  proxy.writeBlob(addr + offset, &nullTerminator, 1);
107  offset++;
108  } else {
109  for (it = strings.begin(); it != strings.end(); it++) {
110  proxy.writeBlob(addr + offset, it->c_str(), it->length() + 1);
111  offset += it->length() + 1;
112  }
113  }
114  proxy.writeBlob(addr + offset, &nullTerminator, 1);
115 }
116 
117 int
119 {
120  int size = 0;
122 
123  for (it = strings.begin(); it != strings.end(); it++) {
124  size += it->length() + 1;
125  }
126 
127  return size + 1;
128 }
129 
130 int
131 X86ISA::smbios::SMBiosStructure::addString(const std::string &new_string)
132 {
133  stringFields = true;
134  // If a string is empty, treat it as not existing. The index for empty
135  // strings is 0.
136  if (new_string.length() == 0)
137  return 0;
138  strings.push_back(new_string);
139  return strings.size();
140 }
141 
142 std::string
144 {
145  assert(n > 0 && n <= strings.size());
146  return strings[n - 1];
147 }
148 
149 void
151  int n, const std::string &new_string)
152 {
153  assert(n > 0 && n <= strings.size());
154  strings[n - 1] = new_string;
155 }
156 
159  startingAddrSegment(p.starting_addr_segment),
160  romSize(p.rom_size),
161  majorVer(p.major), minorVer(p.minor),
162  embContFirmwareMajor(p.emb_cont_firmware_major),
163  embContFirmwareMinor(p.emb_cont_firmware_minor)
164  {
165  vendor = addString(p.vendor);
166  version = addString(p.version);
167  releaseDate = addString(p.release_date);
168 
169  characteristics = composeBitVector(p.characteristics);
171  composeBitVector(p.characteristic_ext_bytes);
172  }
173 
174 uint16_t
176 {
177  uint8_t size = SMBiosStructure::writeOut(proxy, addr);
178 
179  proxy.writeBlob(addr + 0x4, &vendor, 1);
180  proxy.writeBlob(addr + 0x5, &version, 1);
181 
182  uint16_t startingAddrSegmentGuest = htole(startingAddrSegment);
183  proxy.writeBlob(addr + 0x6, &startingAddrSegmentGuest, 2);
184 
185  proxy.writeBlob(addr + 0x8, &releaseDate, 1);
186  proxy.writeBlob(addr + 0x9, &romSize, 1);
187 
188  uint64_t characteristicsGuest = htole(characteristics);
189  proxy.writeBlob(addr + 0xA, &characteristicsGuest, 8);
190 
191  uint16_t characteristicExtBytesGuest =
192  htole(characteristicExtBytes);
193  proxy.writeBlob(addr + 0x12, &characteristicExtBytesGuest, 2);
194 
195  proxy.writeBlob(addr + 0x14, &majorVer, 1);
196  proxy.writeBlob(addr + 0x15, &minorVer, 1);
197  proxy.writeBlob(addr + 0x16, &embContFirmwareMajor, 1);
198  proxy.writeBlob(addr + 0x17, &embContFirmwareMinor, 1);
199 
200  writeOutStrings(proxy, addr + getLength());
201 
202  return size;
203 }
204 
206  SimObject(p), structures(p.structures)
207 {
208  smbiosHeader.majorVersion = p.major_version;
209  smbiosHeader.minorVersion = p.minor_version;
210  assert(p.major_version <= 9);
211  assert(p.minor_version <= 9);
213  (p.major_version << 4) | p.minor_version;
214 }
215 
216 void
218  Addr &headerSize, Addr &structSize)
219 {
220  headerSize = 0x1F;
221 
222  /*
223  * The main header
224  */
225  uint8_t mainChecksum = 0;
226 
227  proxy.writeBlob(addr, (uint8_t *)smbiosHeader.anchorString, 4);
228  for (int i = 0; i < 4; i++)
229  mainChecksum += smbiosHeader.anchorString[i];
230 
231  // The checksum goes here, but we're figuring it out as we go.
232 
233  proxy.writeBlob(addr + 0x5, &smbiosHeader.entryPointLength, 1);
234  mainChecksum += smbiosHeader.entryPointLength;
235  proxy.writeBlob(addr + 0x6, &smbiosHeader.majorVersion, 1);
236  mainChecksum += smbiosHeader.majorVersion;
237  proxy.writeBlob(addr + 0x7, &smbiosHeader.minorVersion, 1);
238  mainChecksum += smbiosHeader.minorVersion;
239  // Maximum structure size goes here, but we'll figure it out later.
240  proxy.writeBlob(addr + 0xA, &smbiosHeader.entryPointRevision, 1);
241  mainChecksum += smbiosHeader.entryPointRevision;
242  proxy.writeBlob(addr + 0xB, &smbiosHeader.formattedArea, 5);
243  for (int i = 0; i < 5; i++)
244  mainChecksum += smbiosHeader.formattedArea[i];
245 
246  /*
247  * The intermediate header
248  */
249  uint8_t intChecksum = 0;
250 
251  proxy.writeBlob(addr + 0x10,
252  smbiosHeader.intermediateHeader.anchorString, 5);
253  for (int i = 0; i < 5; i++)
254  intChecksum += smbiosHeader.intermediateHeader.anchorString[i];
255 
256  // The checksum goes here, but we're figuring it out as we go.
257  // Then the length of the structure table which we'll find later
258 
259  uint32_t tableAddrGuest =
260  htole(smbiosHeader.intermediateHeader.tableAddr);
261  proxy.writeBlob(addr + 0x18, &tableAddrGuest, 4);
262  for (int i = 0; i < 4; i++) {
263  intChecksum += tableAddrGuest;
264  tableAddrGuest >>= 8;
265  }
266 
267  uint16_t numStructs = letoh(structures.size());
268  proxy.writeBlob(addr + 0x1C, &numStructs, 2);
269  for (int i = 0; i < 2; i++) {
270  intChecksum += numStructs;
271  numStructs >>= 8;
272  }
273 
274  proxy.writeBlob(addr + 0x1E,
275  &smbiosHeader.intermediateHeader.smbiosBCDRevision, 1);
276  intChecksum += smbiosHeader.intermediateHeader.smbiosBCDRevision;
277 
278  /*
279  * Structure table
280  */
281 
282  Addr base = smbiosHeader.intermediateHeader.tableAddr;
283  Addr offset = 0;
284  uint16_t maxSize = 0;
286  for (it = structures.begin(); it != structures.end(); it++) {
287  uint16_t size = (*it)->writeOut(proxy, base + offset);
288  if (size > maxSize)
289  maxSize = size;
290  offset += size;
291  }
292 
293  structSize = offset;
294 
295  /*
296  * Header
297  */
298 
299  maxSize = htole(maxSize);
300  proxy.writeBlob(addr + 0x8, &maxSize, 2);
301  for (int i = 0; i < 2; i++) {
302  mainChecksum += maxSize;
303  maxSize >>= 8;
304  }
305 
306  // Set the checksum
307  mainChecksum = -mainChecksum;
308  proxy.writeBlob(addr + 0x4, &mainChecksum, 1);
309 
310  /*
311  * Intermediate header
312  */
313 
314  uint16_t tableSize = offset;
315  tableSize = htole(tableSize);
316  proxy.writeBlob(addr + 0x16, &tableSize, 2);
317  for (int i = 0; i < 2; i++) {
318  intChecksum += tableSize;
319  tableSize >>= 8;
320  }
321 
322  intChecksum = -intChecksum;
323  proxy.writeBlob(addr + 0x15, &intChecksum, 1);
324 }
325 
326 } // namespace gem5
Defines global host-dependent types: Counter, Tick, and (indirectly) {int,uint}{8,...
This object is a proxy for a port or other object which implements the functional response protocol,...
Definition: port_proxy.hh:87
void writeBlob(Addr addr, const void *p, int size) const
Same as tryWriteBlob, but insists on success.
Definition: port_proxy.hh:192
Abstract superclass for simulation objects.
Definition: sim_object.hh:148
uint16_t writeOut(PortProxy &proxy, Addr addr)
Definition: smbios.cc:175
SMBiosStructure(const Params &p, uint8_t _type)
Definition: smbios.cc:89
int addString(const std::string &new_string)
Definition: smbios.cc:131
X86SMBiosSMBiosStructureParams Params
Definition: smbios.hh:71
void setString(int n, const std::string &new_string)
Definition: smbios.cc:150
void writeOutStrings(PortProxy &proxy, Addr addr)
Definition: smbios.cc:95
virtual uint16_t writeOut(PortProxy &proxy, Addr addr)
Definition: smbios.cc:76
void writeOut(PortProxy &proxy, Addr addr, Addr &headerSize, Addr &structSize)
Definition: smbios.cc:217
struct gem5::X86ISA::smbios::SMBiosTable::SMBiosHeader smbiosHeader
SMBiosTable(const Params &p)
Definition: smbios.cc:205
X86SMBiosSMBiosTableParams Params
Definition: smbios.hh:157
STL vector class.
Definition: stl.hh:37
Bitfield< 31 > n
Definition: misc_types.hh:462
Bitfield< 7 > i
Definition: misc_types.hh:67
Bitfield< 25 > vec
Definition: misc.hh:113
Bitfield< 51, 12 > base
Definition: pagetable.hh:141
Bitfield< 63 > val
Definition: misc.hh:776
Bitfield< 3 > addr
Definition: types.hh:84
Bitfield< 0 > p
Definition: pagetable.hh:151
Reference material can be found at the JEDEC website: UFS standard http://www.jedec....
T letoh(T value)
Definition: byteswap.hh:173
uint64_t composeBitVector(T vec)
Definition: smbios.cc:65
uint64_t Addr
Address type This will probably be moved somewhere else in the near future.
Definition: types.hh:147
T htole(T value)
Definition: byteswap.hh:172
Minor contains all the definitions within the MinorCPU apart from the CPU class itself.
PortProxy Object Declaration.
struct gem5::X86ISA::smbios::SMBiosTable::SMBiosHeader::IntermediateHeader intermediateHeader

Generated on Wed Dec 21 2022 10:22:28 for gem5 by doxygen 1.9.1