From 31d8127a156a01e5f664374543b8f1c38ad15a85 Mon Sep 17 00:00:00 2001 From: rtognimp Date: Sat, 24 Apr 2004 10:33:19 +0000 Subject: [PATCH] Some sanity and bound checking git-svn-id: svn://svn.mplayerhq.hu/mplayer/trunk@12267 b3059339-0415-0410-9bf9-f77b7e298cf2 --- libmpdemux/realrtsp/real.c | 49 ++++++++++++++++++++---------- libmpdemux/realrtsp/real.h | 4 +-- libmpdemux/realrtsp/rtsp_session.c | 13 ++++++-- libmpdemux/realrtsp/sdpplin.c | 14 ++++++--- libmpdemux/realrtsp/xbuffer.c | 15 +++++++++ libmpdemux/realrtsp/xbuffer.h | 1 + 6 files changed, 71 insertions(+), 25 deletions(-) diff --git a/libmpdemux/realrtsp/real.c b/libmpdemux/realrtsp/real.c index 8b77fde265..b175514479 100644 --- a/libmpdemux/realrtsp/real.c +++ b/libmpdemux/realrtsp/real.c @@ -35,6 +35,7 @@ #include "real.h" #include "asmrp.h" #include "sdpplin.h" +#include "xbuffer.h" /* #define LOG @@ -422,7 +423,7 @@ void real_calc_response_and_checksum (char *response, char *chksum, char *challe * returns a pointer to selected data and number of bytes in that. */ -static int select_mlti_data(const char *mlti_chunk, int mlti_size, int selection, char *out) { +static int select_mlti_data(const char *mlti_chunk, int mlti_size, int selection, char **out) { int numrules, codec, size; int i; @@ -437,7 +438,7 @@ static int select_mlti_data(const char *mlti_chunk, int mlti_size, int selection #ifdef LOG printf("libreal: MLTI tag not detected, copying data\n"); #endif - memcpy(out, mlti_chunk, mlti_size); + *out = xbuffer_copyin(*out, 0, mlti_chunk, mlti_size); return mlti_size; } @@ -478,7 +479,7 @@ static int select_mlti_data(const char *mlti_chunk, int mlti_size, int selection #ifdef LOG hexdump(mlti_chunk+4, size); #endif - memcpy(out,mlti_chunk+4, size); + *out = xbuffer_copyin(*out, 0, mlti_chunk+4, size); return size; } @@ -486,11 +487,11 @@ static int select_mlti_data(const char *mlti_chunk, int mlti_size, int selection * looking at stream description. */ -rmff_header_t *real_parse_sdp(char *data, char *stream_rules, uint32_t bandwidth) { +rmff_header_t *real_parse_sdp(char *data, char **stream_rules, uint32_t bandwidth) { sdpplin_t *desc; rmff_header_t *header; - char buf[2048]; + char *buf; int len, i; int max_bit_rate=0; int avg_bit_rate=0; @@ -505,6 +506,7 @@ rmff_header_t *real_parse_sdp(char *data, char *stream_rules, uint32_t bandwidth if (!desc) return NULL; + buf = xbuffer_init(2048); header=calloc(1,sizeof(rmff_header_t)); header->fileheader=rmff_new_fileheader(4+desc->stream_count); @@ -535,12 +537,12 @@ rmff_header_t *real_parse_sdp(char *data, char *stream_rules, uint32_t bandwidth printf("asmrp rule match: %u for stream %u\n", rulematches[j], desc->stream[i]->stream_id); #endif sprintf(b,"stream=%u;rule=%u,", desc->stream[i]->stream_id, rulematches[j]); - strcat(stream_rules, b); + *stream_rules = xbuffer_strcat(*stream_rules, b); } if (!desc->stream[i]->mlti_data) return NULL; - len=select_mlti_data(desc->stream[i]->mlti_data, desc->stream[i]->mlti_data_size, rulematches[0], buf); + len=select_mlti_data(desc->stream[i]->mlti_data, desc->stream[i]->mlti_data_size, rulematches[0], &buf); header->streams[i]=rmff_new_mdpr( desc->stream[i]->stream_id, @@ -566,8 +568,8 @@ rmff_header_t *real_parse_sdp(char *data, char *stream_rules, uint32_t bandwidth avg_packet_size=desc->stream[i]->avg_packet_size; } - if (stream_rules) - stream_rules[strlen(stream_rules)-1]=0; /* delete last ',' in stream_rules */ + if (*stream_rules && strlen(*stream_rules) && (*stream_rules)[strlen(*stream_rules)-1] == ',') + (*stream_rules)[strlen(*stream_rules)-1]=0; /* delete last ',' in stream_rules */ header->prop=rmff_new_prop( max_bit_rate, @@ -583,11 +585,12 @@ rmff_header_t *real_parse_sdp(char *data, char *stream_rules, uint32_t bandwidth desc->flags); rmff_fix_header(header); + buf = xbuffer_free(buf); return header; } -int real_get_rdt_chunk(rtsp_t *rtsp_session, char *buffer) { +int real_get_rdt_chunk(rtsp_t *rtsp_session, char **buffer) { int n=1; uint8_t header[8]; @@ -653,9 +656,10 @@ int real_get_rdt_chunk(rtsp_t *rtsp_session, char *buffer) { } else ph.flags=0; - rmff_dump_pheader(&ph, buffer); + *buffer = xbuffer_ensure_size(*buffer, 12+size); + rmff_dump_pheader(&ph, *buffer); size-=12; - n=rtsp_read_data(rtsp_session, buffer+12, size); + n=rtsp_read_data(rtsp_session, (*buffer)+12, size); return n+12; } @@ -687,8 +691,8 @@ rmff_header_t *real_setup_and_get_header(rtsp_t *rtsp_session, uint32_t bandwid char *challenge1; char challenge2[64]; char checksum[34]; - char subscribe[256]; - char buf[256]; + char *subscribe; + char *buf = xbuffer_init(256); char *mrl=rtsp_get_mrl(rtsp_session); unsigned int size; int status; @@ -718,6 +722,7 @@ rmff_header_t *real_setup_and_get_header(rtsp_t *rtsp_session, uint32_t bandwid printf("real: got message from server:\n%s\n", alert); } rtsp_send_ok(rtsp_session); + buf = xbuffer_free(buf); return NULL; } @@ -743,9 +748,14 @@ rmff_header_t *real_setup_and_get_header(rtsp_t *rtsp_session, uint32_t bandwid description[size]=0; /* parse sdp (sdpplin) and create a header and a subscribe string */ + subscribe = xbuffer_init(256); strcpy(subscribe, "Subscribe: "); - h=real_parse_sdp(description, subscribe+11, bandwidth); - if (!h) return NULL; + h=real_parse_sdp(description, &subscribe, bandwidth); + if (!h) { + subscribe = xbuffer_free(subscribe); + buf = xbuffer_free(buf); + return NULL; + } rmff_fix_header(h); #ifdef LOG @@ -755,19 +765,24 @@ rmff_header_t *real_setup_and_get_header(rtsp_t *rtsp_session, uint32_t bandwid /* setup our streams */ real_calc_response_and_checksum (challenge2, checksum, challenge1); + buf = xbuffer_ensure_size(buf, strlen(challenge2) + strlen(checksum) + 32); sprintf(buf, "RealChallenge2: %s, sd=%s", challenge2, checksum); rtsp_schedule_field(rtsp_session, buf); + buf = xbuffer_ensure_size(buf, strlen(session_id) + 32); sprintf(buf, "If-Match: %s", session_id); rtsp_schedule_field(rtsp_session, buf); rtsp_schedule_field(rtsp_session, "Transport: x-pn-tng/tcp;mode=play,rtp/avp/tcp;unicast;mode=play"); + buf = xbuffer_ensure_size(buf, strlen(mrl) + 32); sprintf(buf, "%s/streamid=0", mrl); rtsp_request_setup(rtsp_session,buf); if (h->prop->num_streams > 1) { rtsp_schedule_field(rtsp_session, "Transport: x-pn-tng/tcp;mode=play,rtp/avp/tcp;unicast;mode=play"); + buf = xbuffer_ensure_size(buf, strlen(session_id) + 32); sprintf(buf, "If-Match: %s", session_id); rtsp_schedule_field(rtsp_session, buf); + buf = xbuffer_ensure_size(buf, strlen(mrl) + 32); sprintf(buf, "%s/streamid=1", mrl); rtsp_request_setup(rtsp_session,buf); } @@ -794,5 +809,7 @@ rmff_header_t *real_setup_and_get_header(rtsp_t *rtsp_session, uint32_t bandwid /* and finally send a play request */ rtsp_request_play(rtsp_session,NULL); + subscribe = xbuffer_free(subscribe); + buf = xbuffer_free(buf); return h; } diff --git a/libmpdemux/realrtsp/real.h b/libmpdemux/realrtsp/real.h index f3b9c61bae..410cc4f5c2 100644 --- a/libmpdemux/realrtsp/real.h +++ b/libmpdemux/realrtsp/real.h @@ -38,8 +38,8 @@ * (RealChallenge1 in rtsp). See implementation for details. */ void real_calc_response_and_checksum (char *response, char *chksum, char *challenge); -int real_get_rdt_chunk(rtsp_t *rtsp_session, char *buffer); -rmff_header_t *real_parse_sdp(char *data, char *stream_rules, uint32_t bandwidth); +int real_get_rdt_chunk(rtsp_t *rtsp_session, char **buffer); +rmff_header_t *real_parse_sdp(char *data, char **stream_rules, uint32_t bandwidth); rmff_header_t *real_setup_and_get_header(rtsp_t *rtsp_session, uint32_t bandwidth); #endif diff --git a/libmpdemux/realrtsp/rtsp_session.c b/libmpdemux/realrtsp/rtsp_session.c index 195afa7a64..2cc789fd6f 100644 --- a/libmpdemux/realrtsp/rtsp_session.c +++ b/libmpdemux/realrtsp/rtsp_session.c @@ -45,6 +45,7 @@ #include "real.h" #include "rmff.h" #include "asmrp.h" +#include "xbuffer.h" /* #define LOG @@ -58,7 +59,7 @@ struct rtsp_session_s { rtsp_t *s; /* receive buffer */ - uint8_t recv[BUF_SIZE]; + uint8_t *recv; int recv_size; int recv_read; @@ -78,6 +79,8 @@ rtsp_session_t *rtsp_session_start(int fd, char **mrl, char *path, char *host, i rmff_header_t *h; uint32_t bandwidth=10485800; + rtsp_session->recv = xbuffer_init(BUF_SIZE); + //connect: *redir = 0; @@ -86,6 +89,7 @@ rtsp_session_t *rtsp_session_start(int fd, char **mrl, char *path, char *host, i if (!rtsp_session->s) { printf("rtsp_session: failed to connect to server %s\n", path); + rtsp_session->recv = xbuffer_free(rtsp_session->recv); free(rtsp_session); return NULL; } @@ -124,6 +128,7 @@ rtsp_session_t *rtsp_session_start(int fd, char **mrl, char *path, char *host, i { printf("rtsp_session: session can not be established.\n"); rtsp_close(rtsp_session->s); + rtsp_session->recv = xbuffer_free(rtsp_session->recv); free(rtsp_session); return NULL; } @@ -131,7 +136,7 @@ rtsp_session_t *rtsp_session_start(int fd, char **mrl, char *path, char *host, i rtsp_session->header_len=rmff_dump_header(h,rtsp_session->header,1024); - memcpy(rtsp_session->recv, rtsp_session->header, rtsp_session->header_len); + rtsp_session->recv = xbuffer_copyin(rtsp_session->recv, 0, rtsp_session->header, rtsp_session->header_len); rtsp_session->recv_size = rtsp_session->header_len; rtsp_session->recv_read = 0; @@ -140,6 +145,7 @@ rtsp_session_t *rtsp_session_start(int fd, char **mrl, char *path, char *host, i printf("rtsp_session: Not a Real server. Server type is '%s'.\n",server); rtsp_close(rtsp_session->s); free(server); + rtsp_session->recv = xbuffer_free(rtsp_session->recv); free(rtsp_session); return NULL; } @@ -162,8 +168,8 @@ int rtsp_session_read (rtsp_session_t *this, char *data, int len) { to_copy -= fill; dest += fill; this->recv_read = 0; + this->recv_size = real_get_rdt_chunk (this->s, &(this->recv)); source = this->recv; - this->recv_size = real_get_rdt_chunk (this->s, source); fill = this->recv_size; if (this->recv_size == 0) { @@ -197,5 +203,6 @@ int rtsp_session_peek_header(rtsp_session_t *this, char *buf, int maxsize) { void rtsp_session_end(rtsp_session_t *session) { rtsp_close(session->s); + session->recv = xbuffer_free(session->recv); free(session); } diff --git a/libmpdemux/realrtsp/sdpplin.c b/libmpdemux/realrtsp/sdpplin.c index ce78ffc035..229f4a0e68 100644 --- a/libmpdemux/realrtsp/sdpplin.c +++ b/libmpdemux/realrtsp/sdpplin.c @@ -96,13 +96,19 @@ static char *b64_decode(const char *in, char *out, int *size) static char *nl(char *data) { - return strchr(data,'\n')+1; + char *nlptr = (data) ? strchr(data,'\n') : NULL; + return (nlptr) ? nlptr + 1 : NULL; } static int filter(const char *in, const char *filter, char **out) { int flen=strlen(filter); - int len=strchr(in,'\n')-in; + int len; + + if (!in) + return 0; + + len = (strchr(in,'\n')) ? strchr(in,'\n')-in : strlen(in); if (!strncmp(in,filter,flen)) { @@ -135,7 +141,7 @@ static sdpplin_stream_t *sdpplin_parse_stream(char **data) { } *data=nl(*data); - while (**data && *data[0]!='m') { + while (*data && **data && *data[0]!='m') { handled=0; @@ -236,7 +242,7 @@ sdpplin_t *sdpplin_parse(char *data) { int handled; int len; - while (*data) { + while (data && *data) { handled=0; diff --git a/libmpdemux/realrtsp/xbuffer.c b/libmpdemux/realrtsp/xbuffer.c index 66f99c4b32..de68125ef1 100644 --- a/libmpdemux/realrtsp/xbuffer.c +++ b/libmpdemux/realrtsp/xbuffer.c @@ -85,3 +85,18 @@ void *xbuffer_ensure_size(void *buf, int size) { return buf; } + + + +void *xbuffer_strcat(void *buf, char *data) { + + if (!buf || !data) { + return NULL; + } + + buf = xbuffer_ensure_size(buf, strlen(buf)+strlen(data)+1); + + strcat(buf, data); + + return buf; +} diff --git a/libmpdemux/realrtsp/xbuffer.h b/libmpdemux/realrtsp/xbuffer.h index 4dd4cd7bb8..0ee66c789f 100644 --- a/libmpdemux/realrtsp/xbuffer.h +++ b/libmpdemux/realrtsp/xbuffer.h @@ -21,5 +21,6 @@ void *xbuffer_init(int chunk_size); void *xbuffer_free(void *buf); void *xbuffer_copyin(void *buf, int index, const void *data, int len); void *xbuffer_ensure_size(void *buf, int size); +void *xbuffer_strcat(void *buf, char *data); #endif