| diff --git a/google3/third_party/libsrtp/include/srtp_priv.h b/google3/third_party/libsrtp/include/srtp_priv.h |
| index cf2274e..3bed757 100644 |
| --- a/google3/third_party/libsrtp/include/srtp_priv.h |
| +++ b/google3/third_party/libsrtp/include/srtp_priv.h |
| @@ -189,6 +189,13 @@ srtp_stream_init(srtp_stream_t srtp, |
| |
| |
| /* |
| + * Uninitializes and Deallocates a stream. |
| + */ |
| +err_status_t |
| +srtp_stream_uninit_and_dealloc(srtp_stream_t stream, |
| + srtp_stream_t stream_template); |
| + |
| +/* |
| * libsrtp internal datatypes |
| */ |
| |
| diff --git a/google3/third_party/libsrtp/srtp/srtp.c b/google3/third_party/libsrtp/srtp/srtp.c |
| index 3fc52ee..314c3e4 100644 |
| --- a/google3/third_party/libsrtp/srtp/srtp.c |
| +++ b/google3/third_party/libsrtp/srtp/srtp.c |
| @@ -92,35 +92,31 @@ srtp_stream_alloc(srtp_stream_ctx_t **str_ptr, |
| str = (srtp_stream_ctx_t *) crypto_alloc(sizeof(srtp_stream_ctx_t)); |
| if (str == NULL) |
| return err_status_alloc_fail; |
| - *str_ptr = str; |
| - |
| + *str_ptr = str; |
| + |
| /* allocate cipher */ |
| stat = crypto_kernel_alloc_cipher(p->rtp.cipher_type, |
| &str->rtp_cipher, |
| p->rtp.cipher_key_len); |
| if (stat) { |
| - crypto_free(str); |
| - return stat; |
| + goto err_rtp_cipher_alloc; |
| } |
| |
| /* allocate auth function */ |
| stat = crypto_kernel_alloc_auth(p->rtp.auth_type, |
| &str->rtp_auth, |
| p->rtp.auth_key_len, |
| - p->rtp.auth_tag_len); |
| + p->rtp.auth_tag_len); |
| + |
| if (stat) { |
| - cipher_dealloc(str->rtp_cipher); |
| - crypto_free(str); |
| - return stat; |
| + goto err_rtp_auth_alloc; |
| } |
| - |
| + |
| /* allocate key limit structure */ |
| str->limit = (key_limit_ctx_t*) crypto_alloc(sizeof(key_limit_ctx_t)); |
| if (str->limit == NULL) { |
| - auth_dealloc(str->rtp_auth); |
| - cipher_dealloc(str->rtp_cipher); |
| - crypto_free(str); |
| - return err_status_alloc_fail; |
| + stat = err_status_alloc_fail; |
| + goto err_limit_alloc; |
| } |
| |
| /* |
| @@ -129,13 +125,9 @@ srtp_stream_alloc(srtp_stream_ctx_t **str_ptr, |
| */ |
| stat = crypto_kernel_alloc_cipher(p->rtcp.cipher_type, |
| &str->rtcp_cipher, |
| - p->rtcp.cipher_key_len); |
| + p->rtcp.cipher_key_len); |
| if (stat) { |
| - auth_dealloc(str->rtp_auth); |
| - cipher_dealloc(str->rtp_cipher); |
| - crypto_free(str->limit); |
| - crypto_free(str); |
| - return stat; |
| + goto err_rtcp_cipher_alloc; |
| } |
| |
| /* allocate auth function */ |
| @@ -144,33 +136,37 @@ srtp_stream_alloc(srtp_stream_ctx_t **str_ptr, |
| p->rtcp.auth_key_len, |
| p->rtcp.auth_tag_len); |
| if (stat) { |
| - cipher_dealloc(str->rtcp_cipher); |
| - auth_dealloc(str->rtp_auth); |
| - cipher_dealloc(str->rtp_cipher); |
| - crypto_free(str->limit); |
| - crypto_free(str); |
| - return stat; |
| - } |
| + goto err_rtcp_auth_alloc; |
| + } |
| |
| /* allocate ekt data associated with stream */ |
| stat = ekt_alloc(&str->ekt, p->ekt); |
| if (stat) { |
| - auth_dealloc(str->rtcp_auth); |
| - cipher_dealloc(str->rtcp_cipher); |
| - auth_dealloc(str->rtp_auth); |
| - cipher_dealloc(str->rtp_cipher); |
| - crypto_free(str->limit); |
| - crypto_free(str); |
| - return stat; |
| + goto err_ekt_alloc; |
| } |
| |
| return err_status_ok; |
| + |
| +err_ekt_alloc: |
| + auth_dealloc(str->rtcp_auth); |
| +err_rtcp_auth_alloc: |
| + cipher_dealloc(str->rtcp_cipher); |
| +err_rtcp_cipher_alloc: |
| + crypto_free(str->limit); |
| +err_limit_alloc: |
| + auth_dealloc(str->rtp_auth); |
| +err_rtp_auth_alloc: |
| + cipher_dealloc(str->rtp_cipher); |
| +err_rtp_cipher_alloc: |
| + crypto_free(str); |
| + return stat; |
| } |
| |
| err_status_t |
| -srtp_stream_dealloc(srtp_t session, srtp_stream_ctx_t *stream) { |
| +srtp_stream_dealloc(srtp_stream_ctx_t *stream, |
| + srtp_stream_ctx_t *stream_template) { |
| err_status_t status; |
| - |
| + |
| /* |
| * we use a conservative deallocation strategy - if any deallocation |
| * fails, then we report that fact without trying to deallocate |
| @@ -178,41 +174,29 @@ srtp_stream_dealloc(srtp_t session, srtp_stream_ctx_t *stream) { |
| */ |
| |
| /* deallocate cipher, if it is not the same as that in template */ |
| - if (session->stream_template |
| - && stream->rtp_cipher == session->stream_template->rtp_cipher) { |
| - /* do nothing */ |
| - } else { |
| + if (!stream_template || stream->rtp_cipher != stream_template->rtp_cipher) { |
| status = cipher_dealloc(stream->rtp_cipher); |
| if (status) |
| return status; |
| } |
| |
| /* deallocate auth function, if it is not the same as that in template */ |
| - if (session->stream_template |
| - && stream->rtp_auth == session->stream_template->rtp_auth) { |
| - /* do nothing */ |
| - } else { |
| + if (!stream_template || stream->rtp_auth != stream_template->rtp_auth) { |
| status = auth_dealloc(stream->rtp_auth); |
| if (status) |
| return status; |
| } |
| |
| /* deallocate key usage limit, if it is not the same as that in template */ |
| - if (session->stream_template |
| - && stream->limit == session->stream_template->limit) { |
| - /* do nothing */ |
| - } else { |
| + if (!stream_template || stream->limit != stream_template->limit) { |
| crypto_free(stream->limit); |
| - } |
| + } |
| |
| - /* |
| + /* |
| * deallocate rtcp cipher, if it is not the same as that in |
| - * template |
| + * template |
| */ |
| - if (session->stream_template |
| - && stream->rtcp_cipher == session->stream_template->rtcp_cipher) { |
| - /* do nothing */ |
| - } else { |
| + if (!stream_template || stream->rtcp_cipher != stream_template->rtcp_cipher) { |
| status = cipher_dealloc(stream->rtcp_cipher); |
| if (status) |
| return status; |
| @@ -222,17 +206,14 @@ srtp_stream_dealloc(srtp_t session, srtp_stream_ctx_t *stream) { |
| * deallocate rtcp auth function, if it is not the same as that in |
| * template |
| */ |
| - if (session->stream_template |
| - && stream->rtcp_auth == session->stream_template->rtcp_auth) { |
| - /* do nothing */ |
| - } else { |
| + if (!stream_template || stream->rtcp_auth != stream_template->rtcp_auth) { |
| status = auth_dealloc(stream->rtcp_auth); |
| if (status) |
| return status; |
| } |
| |
| /* DAM - need to deallocate EKT here */ |
| - |
| + |
| /* deallocate srtp stream context */ |
| crypto_free(stream); |
| |
| @@ -549,7 +530,12 @@ srtp_stream_init(srtp_stream_ctx_t *srtp, |
| } |
| |
| return err_status_ok; |
| - } |
| +} |
| + |
| +err_status_t |
| +srtp_stream_uninit(srtp_stream_ctx_t *srtp) { |
| + return rdbx_uninit(&srtp->rtp_rdbx); |
| +} |
| |
| |
| /* |
| @@ -1201,28 +1187,16 @@ srtp_dealloc(srtp_t session) { |
| stream = session->stream_list; |
| while (stream != NULL) { |
| srtp_stream_t next = stream->next; |
| - status = srtp_stream_dealloc(session, stream); |
| - if (status) |
| + status = srtp_stream_uninit_and_dealloc(stream, session->stream_template); |
| + if (status) { |
| return status; |
| + } |
| stream = next; |
| } |
| - |
| + |
| /* deallocate stream template, if there is one */ |
| if (session->stream_template != NULL) { |
| - status = auth_dealloc(session->stream_template->rtcp_auth); |
| - if (status) |
| - return status; |
| - status = cipher_dealloc(session->stream_template->rtcp_cipher); |
| - if (status) |
| - return status; |
| - crypto_free(session->stream_template->limit); |
| - status = cipher_dealloc(session->stream_template->rtp_cipher); |
| - if (status) |
| - return status; |
| - status = auth_dealloc(session->stream_template->rtp_auth); |
| - if (status) |
| - return status; |
| - crypto_free(session->stream_template); |
| + status = srtp_stream_uninit_and_dealloc(session->stream_template, NULL); |
| } |
| |
| /* deallocate session context */ |
| @@ -1287,7 +1261,6 @@ srtp_add_stream(srtp_t session, |
| crypto_free(tmp); |
| return err_status_bad_param; |
| } |
| - |
| return err_status_ok; |
| } |
| |
| @@ -1334,12 +1307,11 @@ srtp_create(srtp_t *session, /* handle for session */ |
| err_status_t |
| srtp_remove_stream(srtp_t session, uint32_t ssrc) { |
| srtp_stream_ctx_t *stream, *last_stream; |
| - err_status_t status; |
| |
| /* sanity check arguments */ |
| if (session == NULL) |
| return err_status_bad_param; |
| - |
| + |
| /* find stream in list; complain if not found */ |
| last_stream = stream = session->stream_list; |
| while ((stream != NULL) && (ssrc != stream->ssrc)) { |
| @@ -1352,8 +1324,20 @@ srtp_remove_stream(srtp_t session, uint32_t ssrc) { |
| /* remove stream from the list */ |
| last_stream->next = stream->next; |
| |
| + return srtp_stream_uninit_and_dealloc(stream, session->stream_template); |
| +} |
| + |
| +err_status_t |
| +srtp_stream_uninit_and_dealloc(srtp_stream_ctx_t *stream, |
| + srtp_stream_ctx_t *stream_template) { |
| + err_status_t status; |
| + /* deallocate rdbx data */ |
| + status = srtp_stream_uninit(stream); |
| + if (status) |
| + return status; |
| + |
| /* deallocate the stream */ |
| - status = srtp_stream_dealloc(session, stream); |
| + status = srtp_stream_dealloc(stream, stream_template); |
| if (status) |
| return status; |
| |