#include #include #include #include #include #include #include #include #define NGX_HTTP_POW_RAND_LEN 64 typedef struct { ngx_uint_t version; ngx_uint_t created; ngx_uint_t validity; ngx_uint_t hardness; u_char random[NGX_HTTP_POW_RAND_LEN]; u_char hmac[EVP_MAX_MD_SIZE]; } ngx_http_pow_challenge; /* const u_char *ngx_http_pow_challenge_to_string(ngx_http_pow_challenge *c, ngx_str_t *str) { u_char random_hex[NGX_HTTP_POW_RAND_LEN * 2 + 1]; u_char hmac_hex[EVP_MAX_MD_SIZE * 2 + 1]; ngx_hex_dump(random_hex, c->random, NGX_HTTP_POW_RAND_LEN); random_hex[NGX_HTTP_POW_RAND_LEN * 2] = 0; ngx_hex_dump(hmac_hex, c->hmac, EVP_MAX_MD_SIZE); hmac_hex[EVP_MAX_MD_SIZE * 2] = 0; char out[1024] = { 0 }; sprintf(out, "version=%lu, created=%lu, validity=%lu, hardness=%lu, random=%s, hmac=%s", c->version, c->created, c->validity, c->hardness, random_hex, hmac_hex); printf("%s\n", out); return NULL; } */ const bool ngx_http_pow_sign_challenge(ngx_http_pow_challenge *c, ngx_str_t *k) { size_t clen; const EVP_MD *digest; clen = sizeof(ngx_http_pow_challenge) - EVP_MAX_MD_SIZE; digest = EVP_sha256(); u_char *hmac = HMAC(digest, k->data, k->len, (const unsigned char *) c, clen, c->hmac, NULL); return hmac == c->hmac; } int main(int argc, char** argv) { ngx_http_pow_challenge c = { .version = 1, .created = 1234567, .validity = 300, .hardness = 22, .random = { 'a', 'b', 'c' }, .hmac = { 0 } }; ngx_str_t key = ngx_string("asdf"); bool success = ngx_http_pow_sign_challenge(&c, &key); printf("Success: %d\n", success); printf("challenge:\n"); printf(" version: %lu\n", c.version); printf(" created: %lu\n", c.created); printf(" validity: %lu\n", c.validity); printf(" hardness: %lu\n", c.hardness); printf(" random: %.*s\n", NGX_HTTP_POW_RAND_LEN, (char *) c.random); printf(" random: %.*s\n", EVP_MAX_MD_SIZE, (char *) c.hmac); // ngx_http_pow_challenge_to_string(&c, NULL); return 0; }