#include #include "memxor.h" #define IPAD 0x36 #define OPAD 0x5c /* Concatenate two preprocessor tokens. */ #define _GLHMAC_CONCAT_(prefix, suffix) prefix##suffix #define _GLHMAC_CONCAT(prefix, suffix) _GLHMAC_CONCAT_(prefix, suffix) #define HMAC_ALG _GLHMAC_CONCAT(sha, GL_HMAC_NAME) #define GL_HMAC_CTX _GLHMAC_CONCAT(HMAC_ALG, _ctx) #define GL_HMAC_FN _GLHMAC_CONCAT(hmac_, HMAC_ALG) #define GL_HMAC_FN_INIT _GLHMAC_CONCAT(HMAC_ALG, _init_ctx) #define GL_HMAC_FN_BLOC _GLHMAC_CONCAT(HMAC_ALG, _process_block) #define GL_HMAC_FN_PROC _GLHMAC_CONCAT(HMAC_ALG, _process_bytes) #define GL_HMAC_FN_FINI _GLHMAC_CONCAT(HMAC_ALG, _finish_ctx) static void hmac_hash(const void* key, size_t keylen, const void* in, size_t inlen, int pad, void* resbuf) { struct GL_HMAC_CTX hmac_ctx; char block[GL_HMAC_BLOCKSIZE]; memset(block, pad, sizeof block); memxor(block, key, keylen); GL_HMAC_FN_INIT(&hmac_ctx); GL_HMAC_FN_BLOC(block, sizeof block, &hmac_ctx); GL_HMAC_FN_PROC(in, inlen, &hmac_ctx); GL_HMAC_FN_FINI(&hmac_ctx, resbuf); } int GL_HMAC_FN(const void* key, size_t keylen, const void* in, size_t inlen, void* resbuf) { char optkeybuf[GL_HMAC_HASHSIZE]; char innerhash[GL_HMAC_HASHSIZE]; /* Ensure key size is <= block size. */ if(keylen > GL_HMAC_BLOCKSIZE) { struct GL_HMAC_CTX keyhash; GL_HMAC_FN_INIT(&keyhash); GL_HMAC_FN_PROC(key, keylen, &keyhash); GL_HMAC_FN_FINI(&keyhash, optkeybuf); key = optkeybuf; /* zero padding of the key to the block size is implicit in the memxor. */ keylen = sizeof optkeybuf; } /* Compute INNERHASH from KEY and IN. */ hmac_hash(key, keylen, in, inlen, IPAD, innerhash); /* Compute result from KEY and INNERHASH. */ hmac_hash(key, keylen, innerhash, sizeof innerhash, OPAD, resbuf); return 0; }