diff --git a/daemon/crypto.c b/daemon/crypto.c index 12092ea85..6a89dce30 100644 --- a/daemon/crypto.c +++ b/daemon/crypto.c @@ -184,7 +184,7 @@ static void prf_n(str *out, char *key, char *x) { /* rfc 3711 section 4.3.1 */ -int crypto_gen_session_key(struct crypto_context *c, str *out, unsigned char label) { +int crypto_gen_session_key(struct crypto_context *c, str *out, unsigned char label, int index_len) { unsigned char key_id[7]; /* [ label, 48-bit ROC || SEQ ] */ unsigned char x[14]; int i; @@ -193,13 +193,13 @@ int crypto_gen_session_key(struct crypto_context *c, str *out, unsigned char lab return -1; ZERO(key_id); - /* key_id[1..6] := r + /* key_id[1..6] := r; or 1..4 for rtcp * key_derivation_rate == 0 --> r == 0 */ key_id[0] = label; memcpy(x, c->master_salt, 14); - for (i = 7; i < 14; i++) - x[i] = key_id[i - 7] ^ x[i]; + for (i = 13 - index_len; i < 14; i++) + x[i] = key_id[i - (13 - index_len)] ^ x[i]; prf_n(out, c->master_key, (char *) x); @@ -268,20 +268,3 @@ static int hmac_sha1_rtcp(struct crypto_context *c, char *out, str *in) { return 0; } - -int crypto_gen_session_keys(struct crypto_context *c) { - str s; - - str_init_len(&s, c->session_key, c->crypto_suite->session_key_len); - if (crypto_gen_session_key(c, &s, 0x00)) - return -1; - str_init_len(&s, c->session_auth_key, c->crypto_suite->srtp_auth_key_len); - if (crypto_gen_session_key(c, &s, 0x01)) - return -1; - str_init_len(&s, c->session_salt, c->crypto_suite->session_salt_len); - if (crypto_gen_session_key(c, &s, 0x02)) - return -1; - - c->have_session_key = 1; - return 0; -} diff --git a/daemon/crypto.h b/daemon/crypto.h index c3c9f8846..a9dca4598 100644 --- a/daemon/crypto.h +++ b/daemon/crypto.h @@ -94,8 +94,7 @@ extern const int num_crypto_suites; const struct crypto_suite *crypto_find_suite(const str *); -int crypto_gen_session_keys(struct crypto_context *c); -int crypto_gen_session_key(struct crypto_context *, str *, unsigned char); +int crypto_gen_session_key(struct crypto_context *, str *, unsigned char, int); static inline int crypto_encrypt_rtp(struct crypto_context *c, struct rtp_header *rtp, str *payload, u_int64_t index) @@ -117,13 +116,6 @@ static inline int crypto_decrypt_rtcp(struct crypto_context *c, struct rtcp_pack { return c->crypto_suite->decrypt_rtcp(c, rtcp, payload, index); } -static inline int crypto_check_session_keys(struct crypto_context *c) { - if (c->have_session_key) - return 0; - if (!c->crypto_suite) - return -1; - return crypto_gen_session_keys(c); -} diff --git a/daemon/rtcp.c b/daemon/rtcp.c index 05dfa9c42..5be75da91 100644 --- a/daemon/rtcp.c +++ b/daemon/rtcp.c @@ -313,6 +313,28 @@ int rtcp_avpf2avp(str *s) { } +static inline int check_session_keys(struct crypto_context *c) { + str s; + + if (c->have_session_key) + return 0; + if (!c->crypto_suite) + return -1; + + str_init_len(&s, c->session_key, c->crypto_suite->session_key_len); + if (crypto_gen_session_key(c, &s, 0x03, 4)) + return -1; + str_init_len(&s, c->session_auth_key, c->crypto_suite->srtcp_auth_key_len); + if (crypto_gen_session_key(c, &s, 0x04, 4)) + return -1; + str_init_len(&s, c->session_salt, c->crypto_suite->session_salt_len); + if (crypto_gen_session_key(c, &s, 0x05, 4)) + return -1; + + c->have_session_key = 1; + return 0; +} + static int rtcp_payload(struct rtcp_packet **out, str *p, const str *s) { struct rtcp_packet *rtcp; @@ -342,7 +364,7 @@ int rtcp_avp2savp(str *s, struct crypto_context *c) { if (rtcp_payload(&rtcp, &payload, s)) return -1; - if (crypto_check_session_keys(c)) + if (check_session_keys(c)) return -1; if (crypto_encrypt_rtcp(c, rtcp, &payload, c->num_packets)) @@ -372,7 +394,7 @@ int rtcp_savp2avp(str *s, struct crypto_context *c) { if (rtcp_payload(&rtcp, &payload, s)) return -1; - if (crypto_check_session_keys(c)) + if (check_session_keys(c)) return -1; if (srtp_payloads(&to_auth, &to_decrypt, &auth_tag, NULL, diff --git a/daemon/rtp.c b/daemon/rtp.c index aa46108bf..1b42102a3 100644 --- a/daemon/rtp.c +++ b/daemon/rtp.c @@ -10,6 +10,28 @@ +static inline int check_session_keys(struct crypto_context *c) { + str s; + + if (c->have_session_key) + return 0; + if (!c->crypto_suite) + return -1; + + str_init_len(&s, c->session_key, c->crypto_suite->session_key_len); + if (crypto_gen_session_key(c, &s, 0x00, 6)) + return -1; + str_init_len(&s, c->session_auth_key, c->crypto_suite->srtp_auth_key_len); + if (crypto_gen_session_key(c, &s, 0x01, 6)) + return -1; + str_init_len(&s, c->session_salt, c->crypto_suite->session_salt_len); + if (crypto_gen_session_key(c, &s, 0x02, 6)) + return -1; + + c->have_session_key = 1; + return 0; +} + static int rtp_payload(struct rtp_header **out, str *p, const str *s) { struct rtp_header *rtp; struct rtp_extension *ext; @@ -111,7 +133,7 @@ int rtp_avp2savp(str *s, struct crypto_context *c) { if (rtp_payload(&rtp, &payload, s)) return -1; - if (crypto_check_session_keys(c)) + if (check_session_keys(c)) return -1; index = packet_index(c, rtp); @@ -142,7 +164,7 @@ int rtp_savp2avp(str *s, struct crypto_context *c) { if (rtp_payload(&rtp, &payload, s)) return -1; - if (crypto_check_session_keys(c)) + if (check_session_keys(c)) return -1; index = packet_index(c, rtp);