diff --git a/common/hmac.c b/common/hmac.c index 6c42fab5d..8cd7436f8 100644 --- a/common/hmac.c +++ b/common/hmac.c @@ -4,15 +4,33 @@ #include #include +void hmac_start(crypto_auth_hmacsha256_state *state, + const void *key, size_t klen) +{ + crypto_auth_hmacsha256_init(state, memcheck(key, klen), klen); +} + +void hmac_update(crypto_auth_hmacsha256_state *state, + const void *src, size_t slen) +{ + crypto_auth_hmacsha256_update(state, memcheck(src, slen), slen); +} + +void hmac_done(crypto_auth_hmacsha256_state *state, + struct hmac *hmac) +{ + crypto_auth_hmacsha256_final(state, hmac->bytes); +} + void hmac(const void *src, size_t slen, const void *key, size_t klen, struct hmac *hmac) { crypto_auth_hmacsha256_state state; - crypto_auth_hmacsha256_init(&state, memcheck(key, klen), klen); - crypto_auth_hmacsha256_update(&state, memcheck(src, slen), slen); - crypto_auth_hmacsha256_final(&state, hmac->bytes); + hmac_start(&state, key, klen); + hmac_update(&state, src, slen); + hmac_done(&state, hmac); } void subkey_from_hmac(const char *prefix, diff --git a/common/hmac.h b/common/hmac.h index 67456c2e7..555239229 100644 --- a/common/hmac.h +++ b/common/hmac.h @@ -16,6 +16,15 @@ void hmac(const void *src, size_t slen, const void *key, size_t klen, struct hmac *hmac); +void hmac_start(crypto_auth_hmacsha256_state *state, + const void *key, size_t klen); + +void hmac_update(crypto_auth_hmacsha256_state *state, + const void *src, size_t slen); + +void hmac_done(crypto_auth_hmacsha256_state *state, + struct hmac *hmac); + /* Common style: hmac to derive key using fixed string prefix. */ void subkey_from_hmac(const char *prefix, const struct secret *base, diff --git a/common/sphinx.c b/common/sphinx.c index 91248d46e..996fb78e8 100644 --- a/common/sphinx.c +++ b/common/sphinx.c @@ -197,11 +197,18 @@ static void xor_cipher_stream(void *dst, const struct secret *k, size_t dstlen) crypto_stream_chacha20_xor(dst, dst, dstlen, nonce, k->data); } -static void compute_hmac(const u8 *src, size_t slen, - const struct secret *key, - struct hmac *h) +/* Convenience function: s2/s2len can be NULL/0 if unwanted */ +static void compute_hmac(const struct secret *key, + const u8 *s1, size_t s1len, + const u8 *s2, size_t s2len, + struct hmac *hmac) { - hmac(src, slen, key->data, sizeof(key->data), h); + crypto_auth_hmacsha256_state state; + + hmac_start(&state, key->data, sizeof(key->data)); + hmac_update(&state, s1, s1len); + hmac_update(&state, s2, s2len); + hmac_done(&state, hmac); } static void compute_packet_hmac(const struct onionpacket *packet, @@ -209,14 +216,10 @@ static void compute_packet_hmac(const struct onionpacket *packet, const struct secret *mukey, struct hmac *hmac) { - u8 mactemp[ROUTING_INFO_SIZE + assocdatalen]; - int pos = 0; - - write_buffer(mactemp, packet->routinginfo, ROUTING_INFO_SIZE, &pos); - write_buffer(mactemp, assocdata, assocdatalen, &pos); - assert(pos == sizeof(mactemp)); - - compute_hmac(mactemp, sizeof(mactemp), mukey, hmac); + compute_hmac(mukey, + packet->routinginfo, ROUTING_INFO_SIZE, + assocdata, assocdatalen, + hmac); } static void generate_header_padding(void *dst, size_t dstlen, @@ -648,7 +651,7 @@ struct onionreply *create_onionreply(const tal_t *ctx, */ subkey_from_hmac("um", shared_secret, &key); - compute_hmac(payload, tal_count(payload), &key, &hmac); + compute_hmac(&key, payload, tal_count(payload), NULL, 0, &hmac); reply->contents = tal_arr(reply, u8, 0), towire_hmac(&reply->contents, &hmac); @@ -708,9 +711,9 @@ u8 *unwrap_onionreply(const tal_t *ctx, /* Check if the HMAC matches, this means that this is * the origin */ subkey_from_hmac("um", &shared_secrets[i], &key); - compute_hmac(r->contents + sizeof(hmac.bytes), + compute_hmac(&key, r->contents + sizeof(hmac.bytes), tal_count(r->contents) - sizeof(hmac.bytes), - &key, &hmac); + NULL, 0, &hmac); if (memcmp(hmac.bytes, r->contents, sizeof(hmac.bytes)) == 0) { *origin_index = i; break;