1 /* 2 // Copyright (c) 2019 Intel Corporation 3 // 4 // Licensed under the Apache License, Version 2.0 (the "License"); 5 // you may not use this file except in compliance with the License. 6 // You may obtain a copy of the License at 7 // 8 // http://www.apache.org/licenses/LICENSE-2.0 9 // 10 // Unless required by applicable law or agreed to in writing, software 11 // distributed under the License is distributed on an "AS IS" BASIS, 12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 // See the License for the specific language governing permissions and 14 // limitations under the License. 15 */ 16 17 #pragma once 18 #include "cpu.hpp" 19 20 #include <sys/stat.h> 21 #include <sys/types.h> 22 #include <unistd.h> 23 24 #include <phosphor-logging/elog-errors.hpp> 25 #include <phosphor-logging/log.hpp> 26 #include <sdbusplus/server.hpp> 27 #include <sdbusplus/timer.hpp> 28 #include <smbios.hpp> 29 #include <xyz/openbmc_project/Smbios/MDR_V2/server.hpp> 30 31 static constexpr int limitEntryLen = 0xff; 32 static constexpr uint8_t mdr2Version = 2; 33 static constexpr uint32_t mdr2SMSize = 0x00100000; 34 static constexpr uint32_t mdr2SMBaseAddress = 0x9FF00000; 35 static constexpr const char* mdrType2File = "/var/lib/smbios/smbios2"; 36 static constexpr const char* mdrV2Path = "/xyz/openbmc_project/Smbios/MDR_V2"; 37 38 enum class MDR2SMBIOSStatusEnum 39 { 40 mdr2Init = 0, 41 mdr2Loaded = 1, 42 mdr2Updated = 2, 43 mdr2Updating = 3 44 }; 45 46 enum class MDR2DirLockEnum 47 { 48 mdr2DirUnlock = 0, 49 mdr2DirLock = 1 50 }; 51 52 typedef struct 53 { 54 uint8_t dataInfo[16]; 55 } DataIdStruct; 56 57 typedef struct 58 { 59 DataIdStruct id; 60 uint32_t size; 61 uint32_t dataSetSize; 62 uint32_t dataVersion; 63 uint32_t timestamp; 64 } Mdr2DirEntry; 65 66 typedef struct 67 { 68 Mdr2DirEntry common; 69 MDR2SMBIOSStatusEnum stage; 70 MDR2DirLockEnum lock; 71 uint16_t lockHandle; 72 uint32_t xferBuff; 73 uint32_t xferSize; 74 uint32_t maxDataSize; 75 uint8_t* dataStorage; 76 } Mdr2DirLocalStruct; 77 78 typedef struct 79 { 80 uint8_t agentVersion; 81 uint8_t dirVersion; 82 uint8_t dirEntries; 83 uint8_t status; // valid / locked / etc 84 uint8_t remoteDirVersion; 85 uint16_t sessionHandle; 86 Mdr2DirLocalStruct dir[maxDirEntries]; 87 } Mdr2DirStruct; 88 89 struct MDRSMBIOSHeader 90 { 91 uint8_t dirVer; 92 uint8_t mdrType; 93 uint32_t timestamp; 94 uint32_t dataSize; 95 } __attribute__((packed)); 96 97 namespace phosphor 98 { 99 namespace smbios 100 { 101 102 class MDR_V2 : sdbusplus::server::object::object< 103 sdbusplus::xyz::openbmc_project::Smbios::server::MDR_V2> 104 { 105 public: 106 MDR_V2() = delete; 107 MDR_V2(const MDR_V2&) = delete; 108 MDR_V2& operator=(const MDR_V2&) = delete; 109 MDR_V2(MDR_V2&&) = delete; 110 MDR_V2& operator=(MDR_V2&&) = delete; 111 ~MDR_V2() = default; 112 113 MDR_V2(sdbusplus::bus::bus& bus, const char* path, sd_event* event) : 114 sdbusplus::server::object::object< 115 sdbusplus::xyz::openbmc_project::Smbios::server::MDR_V2>(bus, path), 116 bus(bus), timer(event, [&](void) { agentSynchronizeData(); }) 117 { 118 119 smbiosDir.agentVersion = smbiosAgentVersion; 120 smbiosDir.dirVersion = 1; 121 smbiosDir.dirEntries = 1; 122 directoryEntries(smbiosDir.dirEntries); 123 smbiosDir.status = 1; 124 smbiosDir.remoteDirVersion = 0; 125 126 std::copy(smbiosTableId.begin(), smbiosTableId.end(), 127 smbiosDir.dir[smbiosDirIndex].common.id.dataInfo); 128 129 smbiosDir.dir[smbiosDirIndex].dataStorage = smbiosTableStorage; 130 131 agentSynchronizeData(); 132 } 133 134 std::vector<uint8_t> getDirectoryInformation(uint8_t dirIndex) override; 135 136 std::vector<uint8_t> getDataInformation(uint8_t idIndex) override; 137 138 bool sendDirectoryInformation(uint8_t dirVersion, uint8_t dirIndex, 139 uint8_t returnedEntries, 140 uint8_t remainingEntries, 141 std::vector<uint8_t> dirEntry) override; 142 143 std::vector<uint8_t> getDataOffer() override; 144 145 bool sendDataInformation(uint8_t idIndex, uint8_t flag, uint32_t dataLen, 146 uint32_t dataVer, uint32_t timeStamp) override; 147 148 int findIdIndex(std::vector<uint8_t> dataInfo) override; 149 150 bool agentSynchronizeData() override; 151 152 std::vector<uint32_t> 153 synchronizeDirectoryCommonData(uint8_t idIndex, uint32_t size) override; 154 155 uint8_t directoryEntries(uint8_t value) override; 156 157 private: 158 Timer timer; 159 160 sdbusplus::bus::bus& bus; 161 162 Mdr2DirStruct smbiosDir; 163 164 bool readDataFromFlash(MDRSMBIOSHeader* mdrHdr, uint8_t* data); 165 166 const std::array<uint8_t, 16> smbiosTableId{ 167 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 0x42}; 168 uint8_t smbiosTableStorage[smbiosTableStorageSize]; 169 170 bool smbiosIsUpdating(uint8_t index); 171 bool smbiosIsAvailForUpdate(uint8_t index); 172 inline uint8_t smbiosValidFlag(uint8_t index); 173 void systemInfoUpdate(void); 174 175 int getTotalCpuSlot(void); 176 std::vector<std::unique_ptr<Cpu>> cpus; 177 }; 178 179 } // namespace smbios 180 } // namespace phosphor 181