// Copyright (c) 2012 The Chromium OS Authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #include "binary_data_utils.h" #include <openssl/md5.h> #include <sys/stat.h> #include <cstddef> #include <cstdlib> #include <cstring> #include <fstream> #include <iomanip> #include "base/logging.h" #include "base/macros.h" namespace { // Number of hex digits in a byte. const int kNumHexDigitsInByte = 2; } // namespace namespace quipper { static uint64_t Md5Prefix(const unsigned char* data, unsigned long length) { uint64_t digest_prefix = 0; unsigned char digest[MD5_DIGEST_LENGTH + 1]; MD5(data, length, digest); // We need 64-bits / # of bits in a byte. std::stringstream ss; for (size_t i = 0; i < sizeof(uint64_t); i++) // The setw(2) and setfill('0') calls are needed to make sure we output 2 // hex characters for every 8-bits of the hash. ss << std::hex << std::setw(2) << std::setfill('0') << static_cast<unsigned int>(digest[i]); ss >> digest_prefix; return digest_prefix; } uint64_t Md5Prefix(const string& input) { auto data = reinterpret_cast<const unsigned char*>(input.data()); return Md5Prefix(data, input.size()); } uint64_t Md5Prefix(const std::vector<char>& input) { auto data = reinterpret_cast<const unsigned char*>(input.data()); return Md5Prefix(data, input.size()); } string RawDataToHexString(const u8* array, size_t length) { // Convert the bytes to hex digits one at a time. // There will be kNumHexDigitsInByte hex digits, and 1 char for NUL. char buffer[kNumHexDigitsInByte + 1]; string result = ""; for (size_t i = 0; i < length; ++i) { snprintf(buffer, sizeof(buffer), "%02x", array[i]); result += buffer; } return result; } string RawDataToHexString(const string& str) { return RawDataToHexString(reinterpret_cast<const u8*>(str.data()), str.size()); } bool HexStringToRawData(const string& str, u8* array, size_t length) { const int kHexRadix = 16; char* err; // Loop through kNumHexDigitsInByte characters at a time (to get one byte) // Stop when there are no more characters, or the array has been filled. for (size_t i = 0; (i + 1) * kNumHexDigitsInByte <= str.size() && i < length; ++i) { string one_byte = str.substr(i * kNumHexDigitsInByte, kNumHexDigitsInByte); array[i] = strtol(one_byte.c_str(), &err, kHexRadix); if (*err) return false; } return true; } } // namespace quipper