1d96e2701SPotin Lai #include <commandutils.hpp> 2d96e2701SPotin Lai #include <groupextcommands.hpp> 3d96e2701SPotin Lai #include <ipmid/api-types.hpp> 4d96e2701SPotin Lai #include <ipmid/api.hpp> 5d96e2701SPotin Lai #include <phosphor-logging/lg2.hpp> 6d96e2701SPotin Lai 7d96e2701SPotin Lai namespace ipmi 8d96e2701SPotin Lai { 9d96e2701SPotin Lai 10d96e2701SPotin Lai PHOSPHOR_LOG2_USING; 11d96e2701SPotin Lai 12d96e2701SPotin Lai uint64_t bigEndianToHost(uint64_t bigEndianValue) 13d96e2701SPotin Lai { 14d96e2701SPotin Lai if (std::endian::native == std::endian::little) 15d96e2701SPotin Lai { 16d96e2701SPotin Lai return std::byteswap(bigEndianValue); 17d96e2701SPotin Lai } 18d96e2701SPotin Lai 19d96e2701SPotin Lai return bigEndianValue; 20d96e2701SPotin Lai } 21d96e2701SPotin Lai 22d96e2701SPotin Lai void registerSBMRFunctions() __attribute__((constructor)); 23d96e2701SPotin Lai 24d96e2701SPotin Lai ipmi::RspType<> ipmiSBMRSendBootProgress(ipmi::Context::ptr ctx, 25d96e2701SPotin Lai std::vector<uint8_t> data) 26d96e2701SPotin Lai { 27d96e2701SPotin Lai using postcode_t = std::tuple<uint64_t, std::vector<uint8_t>>; 28d96e2701SPotin Lai 29d96e2701SPotin Lai std::optional<size_t> hostId = findHost(ctx->hostIdx); 30d96e2701SPotin Lai 31d96e2701SPotin Lai if (!hostId) 32d96e2701SPotin Lai { 33d96e2701SPotin Lai error("Invalid Host Id received"); 34d96e2701SPotin Lai return ipmi::responseInvalidCommand(); 35d96e2701SPotin Lai } 36d96e2701SPotin Lai 37d96e2701SPotin Lai if (data.size() != 9) 38d96e2701SPotin Lai { 39d96e2701SPotin Lai error("Invalid request of boot progress length received: {LENGTH}", 40d96e2701SPotin Lai "LENGTH", data.size()); 41d96e2701SPotin Lai return ipmi::responseReqDataLenInvalid(); 42d96e2701SPotin Lai } 43d96e2701SPotin Lai 44d96e2701SPotin Lai try 45d96e2701SPotin Lai { 46d96e2701SPotin Lai auto primaryPostCode = reinterpret_cast<const uint64_t*>(data.data()); 47d96e2701SPotin Lai auto postCode = postcode_t(bigEndianToHost(*primaryPostCode), data); 48d96e2701SPotin Lai auto conn = getSdBus(); 49*33803b4dSPatrick Williams auto hostbootRawObj = 50*33803b4dSPatrick Williams std::string(bootRawObjPrefix) + std::to_string(*hostId); 51d96e2701SPotin Lai auto method = 52d96e2701SPotin Lai conn->new_method_call(bootRawBusName, hostbootRawObj.data(), 53d96e2701SPotin Lai "org.freedesktop.DBus.Properties", "Set"); 54d96e2701SPotin Lai 55d96e2701SPotin Lai method.append(bootRawIntf, "Value", std::variant<postcode_t>(postCode)); 56d96e2701SPotin Lai 57d96e2701SPotin Lai conn->call_noreply(method); 58d96e2701SPotin Lai } 59d96e2701SPotin Lai catch (std::exception& e) 60d96e2701SPotin Lai { 61d96e2701SPotin Lai error("postcode handler error: {ERROR}", "ERROR", e); 62d96e2701SPotin Lai return ipmi::responseResponseError(); 63d96e2701SPotin Lai } 64d96e2701SPotin Lai 65d96e2701SPotin Lai return ipmi::responseSuccess(); 66d96e2701SPotin Lai } 67d96e2701SPotin Lai 68d96e2701SPotin Lai void registerSBMRFunctions() 69d96e2701SPotin Lai { 70d96e2701SPotin Lai ipmi::registerGroupHandler( 71d96e2701SPotin Lai ipmi::prioOemBase, ipmi::groupSBMR, ipmi::sbmr::cmdSendBootProgress, 72d96e2701SPotin Lai ipmi::Privilege::Admin, ipmiSBMRSendBootProgress); 73d96e2701SPotin Lai return; 74d96e2701SPotin Lai } 75d96e2701SPotin Lai 76d96e2701SPotin Lai } // end of namespace ipmi 77