C++ でIAM認証用 API Gatewayにアクセスするソースコード

#include <stdio.h>
#include <openssl/sha.h>
#include <openssl/hmac.h>
#include <iostream>
#include <string>
#include <time.h>
#include <string.h>
#include <iomanip>
#include <sstream>
#include <string_view>


std::string hmac(std::string key, std::string msg){

    FILE *fp;
    //char *cmdline = "echo -n 'Hello' | openssl dgst -binary -sha256 -hmac 'secret' | base64" ;
    char *cmdline = "echo -n 'key' | openssl dgst -binary -sha256 -hmac 'secret'";
    if ((fp=popen(cmdline, "r")) == NULL) {
        perror ("popen failed");
        exit(EXIT_FAILURE);
    }
    char buf[256];
    while(fgets(buf, sizeof(buf), fp) != NULL) {
        printf("=> %s", buf);
    }

    pclose(fp);
    std::string signing_key(buf);
    return signing_key;
}

std::string hmac_hex(std::string key, std::string msg){

    FILE *fp;
    //char *cmdline = "echo -n 'Hello' | openssl dgst -binary -sha256 -hmac 'secret' | base64" ;
    char *cmdline = "echo -n 'Hello' | openssl dgst -hex  -sha256 -hmac 'secret'";
    if ((fp=popen(cmdline, "r")) == NULL) {
        perror ("popen failed");
        exit(EXIT_FAILURE);
    }
    char buf[256];
    while(fgets(buf, sizeof(buf), fp) != NULL) {
        printf("=> %s", buf);
    }

    pclose(fp);
    std::string signing_key(buf);
    return signing_key;
}

std::string sha256(const std::string str){
  unsigned char hash[SHA256_DIGEST_LENGTH];

  SHA256_CTX sha256;
  SHA256_Init(&sha256);
  SHA256_Update(&sha256, str.c_str(), str.size());
  SHA256_Final(hash, &sha256);

  std::stringstream ss;

  for(int i = 0; i < SHA256_DIGEST_LENGTH; i++){
    ss << std::hex << std::setw(2) << std::setfill('0') << static_cast<int>( hash[i] );
  }

  return ss.str();
}

using namespace std;
int main(int argc, char *argv[])
{

    std::cout <<"start"<< std::endl;
    string host = "host";
    string stage = "dev";
    string region = "";
    string access_key ="";
    string secret_key = "";
    string method = "POST";
    time_t now;
    
    struct tm *ptm;
    char amz_date[128];
    now = time(NULL);
    ptm = gmtime(&now);
    strftime(amz_date, sizeof(amz_date),"%Y%m%d%H%M%SZ",ptm);
    char date_stamp[128];
    printf("amz_date : %s\n", amz_date);
    strftime(date_stamp, sizeof(date_stamp),"%Y%m%d",ptm);
    printf("amz_date : %s\n", date_stamp);
    string s_date_stamp(date_stamp);
    string request_parameters = "\0";
    string credential_scope = s_date_stamp + "/ap-northeast-1/execute-api/aws4_request";
    printf("credential scope :");
    std::cout <<credential_scope<< std::endl;
    string signed_headers = "host;x-amz-date";
    string s_amz_date(amz_date);
    string canonical_headers = "host:"+ host + "\nx-amz-date:" +s_amz_date + "\n";
    printf("canonical_headers :\n");
    std::cout <<canonical_headers<< std::endl;
    string payload_hash(sha256(request_parameters));

    printf("payload_hash :\n");
    std::cout <<payload_hash<< std::endl;
    string canonical_request = method + "\n" + stage + "/\n\n" + canonical_headers + "\n" + signed_headers + "\n" + payload_hash;
    printf("canonical_request :\n");
    std::cout <<canonical_request<< std::endl;
    string canonical_request_hash = sha256(canonical_request);
    printf("canonical_request_hash :\n");
    std::cout <<canonical_request_hash<< std::endl;
    string target_data = "AWS4-HMAC-SHA256\n" + s_amz_date + "\n" + credential_scope +  "\n" + canonical_request_hash;
    printf("target_data :\n");
    std::cout <<target_data<< std::endl;
    string tmp = "AWS4"+ secret_key;
    string signing_key = hmac(tmp,s_date_stamp);
    printf("signing_key :\n");
    std::cout <<signing_key<< std::endl;

    signing_key = hmac(signing_key,region);
    printf("signing_key :\n");
    std::cout <<signing_key<< std::endl;
    
    signing_key = hmac(signing_key,"execute-api");
    printf("signing_key :\n");
    std::cout <<signing_key<< std::endl;

    signing_key = hmac(signing_key,"aws4_request");
    printf("signing_key :\n");
    std::cout <<signing_key<< std::endl;

    string signature = hmac_hex(signing_key,target_data);

    printf("signature :\n");
    std::cout <<signing_key<< std::endl;

    string authorization_header ="AWS4-HMAC-SHA256 Credential="+access_key + "/"+ credential_scope+",SignedHeaders="+ signed_headers+",Signature="+signature;

    printf("authorization_header :\n");
    std::cout <<authorization_header<< std::endl;


    



}