The Pedigree Project  0.1
SMBios.cc
1 /*
2  * Copyright (c) 2008-2014, Pedigree Developers
3  *
4  * Please see the CONTRIB file in the root of the source tree for a full
5  * list of contributors.
6  *
7  * Permission to use, copy, modify, and distribute this software for any
8  * purpose with or without fee is hereby granted, provided that the above
9  * copyright notice and this permission notice appear in all copies.
10  *
11  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
12  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
13  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
14  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
15  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
16  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
17  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
18  */
19 
20 #if defined(SMBIOS)
21 
22 #include "SMBios.h"
23 #include "pedigree/kernel/Log.h"
24 #include "pedigree/kernel/utilities/utility.h"
25 
26 void SMBios::initialise()
27 {
28  // Search for the SMBIOS tables
29  find();
30  if (m_pEntryPoint == 0)
31  {
32  NOTICE("SMBios: not compliant to the SMBIOS Specification");
33  return;
34  }
35 
36  NOTICE(
37  "SMBIOS Specification " << Dec << m_pEntryPoint->majorVersion << "."
38  << m_pEntryPoint->minorVersion);
39  NOTICE(
40  " entry-point at " << Hex
41  << reinterpret_cast<uintptr_t>(m_pEntryPoint));
42  NOTICE(
43  " tables at " << Hex << m_pEntryPoint->tableAddress << " - "
44  << (m_pEntryPoint->tableAddress +
45  m_pEntryPoint->tableLength));
46 
47  // Go through the tables
48  Header *pCurHeader =
49  reinterpret_cast<Header *>(m_pEntryPoint->tableAddress);
50  for (size_t i = 0; i < m_pEntryPoint->structureCount; i++)
51  {
52  switch (pCurHeader->type)
53  {
54  case 0:
55  {
56  BiosInformation *pBiosInfo =
57  reinterpret_cast<BiosInformation *>(
58  adjust_pointer(pCurHeader, sizeof(Header)));
59  NOTICE(" BIOS Information:");
60  NOTICE(
61  " vendor \""
62  << getString(pCurHeader, pBiosInfo->vendorIndex) << "\"");
63  NOTICE(
64  " version \""
65  << getString(pCurHeader, pBiosInfo->biosVersionIndex)
66  << "\"");
67  NOTICE(
68  " release data \""
69  << getString(pCurHeader, pBiosInfo->biosReleaseDateIndex)
70  << "\"");
71  NOTICE(
72  " memory: "
73  << Hex
74  << (static_cast<size_t>(pBiosInfo->biosStartSegment) * 16)
75  << " - "
76  << (static_cast<size_t>(pBiosInfo->biosStartSegment) * 16 +
77  64 * 1024 *
78  (static_cast<size_t>(pBiosInfo->biosRomSize) + 1)));
79  NOTICE(
80  " characteristics: " << Hex
81  << pBiosInfo->biosCharacteristics);
82  // TODO: extended characteristics
83  }
84  break;
85  default:
86  {
87  NOTICE(
88  " unknown structure (" << Hex << pCurHeader->type << ")");
89  }
90  }
91 
92  pCurHeader = next(pCurHeader);
93  }
94 }
95 
96 SMBios::Header *SMBios::next(Header *pHeader)
97 {
98  uint16_t *stringTable =
99  reinterpret_cast<uint16_t *>(adjust_pointer(pHeader, pHeader->length));
100  while (*stringTable != 0)
101  stringTable = adjust_pointer(stringTable, 1);
102  return reinterpret_cast<Header *>(++stringTable);
103 }
104 
105 const char *SMBios::getString(const Header *pHeader, size_t index)
106 {
107  const char *pCur = reinterpret_cast<const char *>(
108  adjust_pointer(pHeader, pHeader->length));
109  for (size_t i = 1; i < index; i++)
110  while (*pCur++ != '\0')
111  ;
112  return pCur;
113 }
114 
115 void SMBios::find()
116 {
117  m_pEntryPoint = reinterpret_cast<EntryPoint *>(0xF0000);
118  while (reinterpret_cast<uintptr_t>(m_pEntryPoint) < 0x100000)
119  {
120  if (m_pEntryPoint->signature == 0x5F4D535F &&
121  m_pEntryPoint->signature2[0] == 0x5F &&
122  m_pEntryPoint->signature2[1] == 0x44 &&
123  m_pEntryPoint->signature2[2] == 0x4D &&
124  m_pEntryPoint->signature2[3] == 0x49 &&
125  m_pEntryPoint->signature2[4] == 0x5F &&
126  checksum(m_pEntryPoint) == true)
127  return;
128  m_pEntryPoint = adjust_pointer(m_pEntryPoint, 16);
129  }
130  m_pEntryPoint = 0;
131 }
132 
133 bool SMBios::checksum(const EntryPoint *pEntryPoint)
134 {
135  if (::checksum(
136  reinterpret_cast<const uint8_t *>(pEntryPoint),
137  pEntryPoint->length) == false)
138  return false;
139 
140  return ::checksum(
141  reinterpret_cast<const uint8_t *>(&pEntryPoint->signature2[0]), 0x0F);
142 }
143 
144 SMBios::SMBios() : m_pEntryPoint(0)
145 {
146 }
147 SMBios::~SMBios()
148 {
149 }
150 
151 #endif
struct pbuf * next
Definition: pbuf.h:163
#define NOTICE(text)
Definition: Log.h:74
Definition: Log.h:136
Definition: Log.h:138