21 #include "kinetic/hmac_provider.h"
24 #include <arpa/inet.h>
26 #include <openssl/hmac.h>
27 #include <openssl/sha.h>
28 #include "glog/logging.h"
32 using com::seagate::kinetic::client::proto::Message;
34 HmacProvider::HmacProvider() {}
36 std::string HmacProvider::ComputeHmac(
const Message& message,
37 const std::string& key)
const {
40 HMAC_Init_ex(&ctx, key.c_str(), key.length(), EVP_sha1(), NULL);
42 if (message.commandbytes().length() != 0) {
43 uint32_t message_length_bigendian = htonl(message.commandbytes().length());
44 HMAC_Update(&ctx, reinterpret_cast<unsigned char *>(&message_length_bigendian),
46 HMAC_Update(&ctx, reinterpret_cast<const unsigned char *>(message.commandbytes().c_str()),
47 message.commandbytes().length());
50 unsigned char result[SHA_DIGEST_LENGTH];
51 unsigned int result_length = SHA_DIGEST_LENGTH;
52 HMAC_Final(&ctx, result, &result_length);
53 HMAC_CTX_cleanup(&ctx);
55 return std::string(reinterpret_cast<char *>(result), result_length);
58 bool HmacProvider::ValidateHmac(
const Message& message,
const std::string& key)
const {
59 std::string correct_hmac(ComputeHmac(message, key));
61 if (!message.has_hmacauth()) {
65 const std::string &provided_hmac = message.hmacauth().hmac();
67 if (provided_hmac.length() != correct_hmac.length()) {
72 for (
size_t i = 0; i < correct_hmac.length(); i++) {
73 result |= provided_hmac[i] ^ correct_hmac[i];