1*40e9b92eSEd Tanous // SPDX-License-Identifier: Apache-2.0 2*40e9b92eSEd Tanous // SPDX-FileCopyrightText: Copyright OpenBMC Authors 3f201ffb4SEd Tanous #pragma once 4f201ffb4SEd Tanous 5f201ffb4SEd Tanous #include <array> 69ea15c35SEd Tanous #include <cstddef> 7d5c80ad9SNan Zhou #include <cstdint> 8f201ffb4SEd Tanous #include <string> 94cee35e7SVidya Satyamsetti #include <vector> 10f201ffb4SEd Tanous 11f201ffb4SEd Tanous static constexpr std::array<char, 16> digitsArray = { 12f201ffb4SEd Tanous '0', '1', '2', '3', '4', '5', '6', '7', 13f201ffb4SEd Tanous '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'}; 144cee35e7SVidya Satyamsetti 154cee35e7SVidya Satyamsetti inline std::string intToHexString(uint64_t value, size_t digits) 164cee35e7SVidya Satyamsetti { 17f201ffb4SEd Tanous std::string rc(digits, '0'); 18f201ffb4SEd Tanous size_t bitIndex = (digits - 1) * 4; 19f201ffb4SEd Tanous for (size_t digitIndex = 0; digitIndex < digits; digitIndex++) 20f201ffb4SEd Tanous { 21f201ffb4SEd Tanous rc[digitIndex] = digitsArray[(value >> bitIndex) & 0x0f]; 22f201ffb4SEd Tanous bitIndex -= 4; 23f201ffb4SEd Tanous } 24f201ffb4SEd Tanous return rc; 25f201ffb4SEd Tanous } 264cee35e7SVidya Satyamsetti 274cee35e7SVidya Satyamsetti inline std::string bytesToHexString(const std::vector<uint8_t>& bytes) 284cee35e7SVidya Satyamsetti { 294cee35e7SVidya Satyamsetti std::string rc(bytes.size() * 2, '0'); 304cee35e7SVidya Satyamsetti for (size_t i = 0; i < bytes.size(); ++i) 314cee35e7SVidya Satyamsetti { 324cee35e7SVidya Satyamsetti rc[i * 2] = digitsArray[(bytes[i] & 0xf0) >> 4]; 334cee35e7SVidya Satyamsetti rc[i * 2 + 1] = digitsArray[bytes[i] & 0x0f]; 344cee35e7SVidya Satyamsetti } 354cee35e7SVidya Satyamsetti return rc; 364cee35e7SVidya Satyamsetti } 374cee35e7SVidya Satyamsetti 384cee35e7SVidya Satyamsetti // Returns nibble. 394cee35e7SVidya Satyamsetti inline uint8_t hexCharToNibble(char ch) 404cee35e7SVidya Satyamsetti { 414cee35e7SVidya Satyamsetti uint8_t rc = 16; 424cee35e7SVidya Satyamsetti if (ch >= '0' && ch <= '9') 434cee35e7SVidya Satyamsetti { 444cee35e7SVidya Satyamsetti rc = static_cast<uint8_t>(ch) - '0'; 454cee35e7SVidya Satyamsetti } 464cee35e7SVidya Satyamsetti else if (ch >= 'A' && ch <= 'F') 474cee35e7SVidya Satyamsetti { 48b5b62cc1SWilly Tu rc = static_cast<uint8_t>(ch - 'A') + 10U; 494cee35e7SVidya Satyamsetti } 504cee35e7SVidya Satyamsetti else if (ch >= 'a' && ch <= 'f') 514cee35e7SVidya Satyamsetti { 52b5b62cc1SWilly Tu rc = static_cast<uint8_t>(ch - 'a') + 10U; 534cee35e7SVidya Satyamsetti } 544cee35e7SVidya Satyamsetti 554cee35e7SVidya Satyamsetti return rc; 564cee35e7SVidya Satyamsetti } 574cee35e7SVidya Satyamsetti 584cee35e7SVidya Satyamsetti // Returns empty vector in case of malformed hex-string. 594cee35e7SVidya Satyamsetti inline std::vector<uint8_t> hexStringToBytes(const std::string& str) 604cee35e7SVidya Satyamsetti { 614cee35e7SVidya Satyamsetti std::vector<uint8_t> rc(str.size() / 2, 0); 624cee35e7SVidya Satyamsetti for (size_t i = 0; i < str.length(); i += 2) 634cee35e7SVidya Satyamsetti { 644cee35e7SVidya Satyamsetti uint8_t hi = hexCharToNibble(str[i]); 654cee35e7SVidya Satyamsetti if (i == str.length() - 1) 664cee35e7SVidya Satyamsetti { 674cee35e7SVidya Satyamsetti return {}; 684cee35e7SVidya Satyamsetti } 694cee35e7SVidya Satyamsetti uint8_t lo = hexCharToNibble(str[i + 1]); 704cee35e7SVidya Satyamsetti if (lo == 16 || hi == 16) 714cee35e7SVidya Satyamsetti { 724cee35e7SVidya Satyamsetti return {}; 734cee35e7SVidya Satyamsetti } 744cee35e7SVidya Satyamsetti 754cee35e7SVidya Satyamsetti rc[i / 2] = static_cast<uint8_t>(hi << 4) | lo; 764cee35e7SVidya Satyamsetti } 774cee35e7SVidya Satyamsetti return rc; 784cee35e7SVidya Satyamsetti } 79