From 1b9ea3239d22147e00d8cccb666cd8f9344b181e Mon Sep 17 00:00:00 2001 From: Daniel Stenberg Date: Thu, 16 Mar 2023 12:11:46 +0100 Subject: [PATCH] rtsp: use dynbuf instead of custom reallocs For the RTP buffering. Closes #10776 --- lib/rtsp.c | 46 +++++++++++++--------------------------------- lib/rtsp.h | 5 +++-- 2 files changed, 16 insertions(+), 35 deletions(-) diff --git a/lib/rtsp.c b/lib/rtsp.c index aef3560a9..6dd69a245 100644 --- a/lib/rtsp.c +++ b/lib/rtsp.c @@ -119,6 +119,7 @@ const struct Curl_handler Curl_handler_rtsp = { PROTOPT_NONE /* flags */ }; +#define MAX_RTP_BUFFERSIZE 1000000 /* arbitrary */ static CURLcode rtsp_setup_connection(struct Curl_easy *data, struct connectdata *conn) @@ -130,6 +131,7 @@ static CURLcode rtsp_setup_connection(struct Curl_easy *data, if(!rtsp) return CURLE_OUT_OF_MEMORY; + Curl_dyn_init(&conn->proto.rtspc.buf, MAX_RTP_BUFFERSIZE); return CURLE_OK; } @@ -176,7 +178,7 @@ static CURLcode rtsp_disconnect(struct Curl_easy *data, { (void) dead; (void) data; - Curl_safefree(conn->proto.rtspc.rtp_buf); + Curl_dyn_free(&conn->proto.rtspc.buf); return CURLE_OK; } @@ -597,23 +599,14 @@ static CURLcode rtsp_rtp_readwrite(struct Curl_easy *data, char *rtp; /* moving pointer to rtp data */ ssize_t rtp_dataleft; /* how much data left to parse in this round */ - char *scratch; CURLcode result; - if(rtspc->rtp_buf) { - /* There was some leftover data the last time. Merge buffers */ - char *newptr = Curl_saferealloc(rtspc->rtp_buf, - rtspc->rtp_bufsize + *nread); - if(!newptr) { - rtspc->rtp_buf = NULL; - rtspc->rtp_bufsize = 0; + if(Curl_dyn_len(&rtspc->buf)) { + /* There was some leftover data the last time. Append new buffers */ + if(Curl_dyn_addn(&rtspc->buf, k->str, *nread)) return CURLE_OUT_OF_MEMORY; - } - rtspc->rtp_buf = newptr; - memcpy(rtspc->rtp_buf + rtspc->rtp_bufsize, k->str, *nread); - rtspc->rtp_bufsize += *nread; - rtp = rtspc->rtp_buf; - rtp_dataleft = rtspc->rtp_bufsize; + rtp = Curl_dyn_ptr(&rtspc->buf); + rtp_dataleft = Curl_dyn_len(&rtspc->buf); } else { /* Just parse the request buffer directly */ @@ -641,14 +634,11 @@ static CURLcode rtsp_rtp_readwrite(struct Curl_easy *data, /* We have the full RTP interleaved packet * Write out the header including the leading '$' */ DEBUGF(infof(data, "RTP write channel %d rtp_length %d", - rtspc->rtp_channel, rtp_length)); + rtspc->rtp_channel, rtp_length)); result = rtp_client_write(data, &rtp[0], rtp_length + 4); if(result) { failf(data, "Got an error writing an RTP packet"); *readmore = FALSE; - Curl_safefree(rtspc->rtp_buf); - rtspc->rtp_buf = NULL; - rtspc->rtp_bufsize = 0; return result; } @@ -672,20 +662,12 @@ static CURLcode rtsp_rtp_readwrite(struct Curl_easy *data, if(rtp_dataleft && rtp[0] == '$') { DEBUGF(infof(data, "RTP Rewinding %zd %s", rtp_dataleft, - *readmore ? "(READMORE)" : "")); + *readmore ? "(READMORE)" : "")); /* Store the incomplete RTP packet for a "rewind" */ - scratch = malloc(rtp_dataleft); - if(!scratch) { - Curl_safefree(rtspc->rtp_buf); - rtspc->rtp_buf = NULL; - rtspc->rtp_bufsize = 0; + Curl_dyn_reset(&rtspc->buf); + if(Curl_dyn_addn(&rtspc->buf, rtp, rtp_dataleft)) return CURLE_OUT_OF_MEMORY; - } - memcpy(scratch, rtp, rtp_dataleft); - Curl_safefree(rtspc->rtp_buf); - rtspc->rtp_buf = scratch; - rtspc->rtp_bufsize = rtp_dataleft; /* As far as the transfer is concerned, this data is consumed */ *nread = 0; @@ -705,9 +687,7 @@ static CURLcode rtsp_rtp_readwrite(struct Curl_easy *data, *nread = rtp_dataleft; /* If we get here, we have finished with the leftover/merge buffer */ - Curl_safefree(rtspc->rtp_buf); - rtspc->rtp_buf = NULL; - rtspc->rtp_bufsize = 0; + Curl_dyn_free(&rtspc->buf); return CURLE_OK; } diff --git a/lib/rtsp.h b/lib/rtsp.h index 6e55616b3..6bce41a61 100644 --- a/lib/rtsp.h +++ b/lib/rtsp.h @@ -29,6 +29,8 @@ #ifndef CURL_DISABLE_RTSP +#include "dynbuf.h" + extern const struct Curl_handler Curl_handler_rtsp; CURLcode Curl_rtsp_parseheader(struct Curl_easy *data, char *header); @@ -45,8 +47,7 @@ CURLcode Curl_rtsp_parseheader(struct Curl_easy *data, char *header); * Currently, only used for tracking incomplete RTP data reads */ struct rtsp_conn { - char *rtp_buf; - ssize_t rtp_bufsize; + struct dynbuf buf; int rtp_channel; };