summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/combined/ffmpeg/ff_audio_decoder.c2
-rw-r--r--src/combined/ffmpeg/ff_video_decoder.c24
-rw-r--r--src/demuxers/demux_aac.c2
-rw-r--r--src/demuxers/demux_ac3.c8
-rw-r--r--src/demuxers/demux_asf.c10
-rw-r--r--src/demuxers/demux_dts.c2
-rw-r--r--src/demuxers/demux_matroska.c53
-rw-r--r--src/demuxers/demux_mng.c10
-rw-r--r--src/demuxers/demux_mod.c9
-rw-r--r--src/demuxers/demux_mpc.c2
-rw-r--r--src/demuxers/demux_mpeg.c18
-rw-r--r--src/demuxers/demux_mpeg_block.c6
-rw-r--r--src/demuxers/demux_mpeg_pes.c2
-rw-r--r--src/demuxers/demux_nsf.c2
-rw-r--r--src/demuxers/demux_ogg.c2
-rw-r--r--src/demuxers/demux_qt.c33
-rw-r--r--src/demuxers/demux_real.c51
-rw-r--r--src/demuxers/demux_realaudio.c18
-rw-r--r--src/demuxers/demux_shn.c2
-rw-r--r--src/demuxers/demux_slave.c5
-rw-r--r--src/demuxers/demux_ts.c2
-rw-r--r--src/demuxers/demux_tta.c4
-rw-r--r--src/demuxers/demux_vox.c2
-rw-r--r--src/demuxers/demux_yuv_frames.c10
-rw-r--r--src/input/input_dvb.c4
-rw-r--r--src/input/input_dvd.c3
-rw-r--r--src/input/input_file.c8
-rw-r--r--src/input/input_gnome_vfs.c5
-rw-r--r--src/input/input_http.c15
-rw-r--r--src/input/input_mms.c5
-rw-r--r--src/input/input_net.c12
-rw-r--r--src/input/input_pnm.c18
-rw-r--r--src/input/input_pvr.c6
-rw-r--r--src/input/input_rtp.c12
-rw-r--r--src/input/input_rtsp.c18
-rw-r--r--src/input/input_smb.c7
-rw-r--r--src/input/input_stdin_fifo.c13
-rw-r--r--src/libsputext/demux_sputext.c2
38 files changed, 319 insertions, 88 deletions
diff --git a/src/combined/ffmpeg/ff_audio_decoder.c b/src/combined/ffmpeg/ff_audio_decoder.c
index 2a6c04dd3..a9f630506 100644
--- a/src/combined/ffmpeg/ff_audio_decoder.c
+++ b/src/combined/ffmpeg/ff_audio_decoder.c
@@ -249,6 +249,8 @@ static void ff_audio_decode_data (audio_decoder_t *this_gen, buf_element_t *buf)
if (extradata + data_len > this->size)
break; /* abort early - extradata length is bad */
+ if (extradata > INT_MAX - data_len)
+ break;/*integer overflow*/
this->context->extradata_size = data_len;
this->context->extradata = malloc(this->context->extradata_size +
diff --git a/src/combined/ffmpeg/ff_video_decoder.c b/src/combined/ffmpeg/ff_video_decoder.c
index f4f7175fa..a1ab3696c 100644
--- a/src/combined/ffmpeg/ff_video_decoder.c
+++ b/src/combined/ffmpeg/ff_video_decoder.c
@@ -609,6 +609,10 @@ static void ff_convert_frame(ff_video_decoder_t *this, vo_frame_t *img) {
su = this->av_frame->data[1];
sv = this->av_frame->data[2];
+ /* Some segfaults & heap corruption have been observed with img->height,
+ * so we use this->bih.biHeight instead (which is the displayed height)
+ */
+
if (this->context->pix_fmt == PIX_FMT_YUV410P) {
yuv9_to_yv12(
@@ -629,7 +633,7 @@ static void ff_convert_frame(ff_video_decoder_t *this, vo_frame_t *img) {
img->pitches[2],
/* width x height */
img->width,
- img->height);
+ this->bih.biHeight);
} else if (this->context->pix_fmt == PIX_FMT_YUV411P) {
@@ -651,7 +655,7 @@ static void ff_convert_frame(ff_video_decoder_t *this, vo_frame_t *img) {
img->pitches[2],
/* width x height */
img->width,
- img->height);
+ this->bih.biHeight);
} else if (this->context->pix_fmt == PIX_FMT_RGBA32) {
@@ -659,7 +663,7 @@ static void ff_convert_frame(ff_video_decoder_t *this, vo_frame_t *img) {
uint32_t *argb_pixels;
uint32_t argb;
- for(y = 0; y < img->height; y++) {
+ for(y = 0; y < this->bih.biHeight; y++) {
argb_pixels = (uint32_t *)sy;
for(x = 0; x < img->width; x++) {
uint8_t r, g, b;
@@ -687,7 +691,7 @@ static void ff_convert_frame(ff_video_decoder_t *this, vo_frame_t *img) {
uint8_t *src;
uint16_t pixel16;
- for(y = 0; y < img->height; y++) {
+ for(y = 0; y < this->bih.biHeight; y++) {
src = sy;
for(x = 0; x < img->width; x++) {
uint8_t r, g, b;
@@ -716,7 +720,7 @@ static void ff_convert_frame(ff_video_decoder_t *this, vo_frame_t *img) {
uint8_t *src;
uint16_t pixel16;
- for(y = 0; y < img->height; y++) {
+ for(y = 0; y < this->bih.biHeight; y++) {
src = sy;
for(x = 0; x < img->width; x++) {
uint8_t r, g, b;
@@ -744,7 +748,7 @@ static void ff_convert_frame(ff_video_decoder_t *this, vo_frame_t *img) {
int x, plane_ptr = 0;
uint8_t *src;
- for(y = 0; y < img->height; y++) {
+ for(y = 0; y < this->bih.biHeight; y++) {
src = sy;
for(x = 0; x < img->width; x++) {
uint8_t r, g, b;
@@ -768,7 +772,7 @@ static void ff_convert_frame(ff_video_decoder_t *this, vo_frame_t *img) {
int x, plane_ptr = 0;
uint8_t *src;
- for(y = 0; y < img->height; y++) {
+ for(y = 0; y < this->bih.biHeight; y++) {
src = sy;
for(x = 0; x < img->width; x++) {
uint8_t r, g, b;
@@ -811,7 +815,7 @@ static void ff_convert_frame(ff_video_decoder_t *this, vo_frame_t *img) {
v_palette[x] = COMPUTE_V(r, g, b);
}
- for(y = 0; y < img->height; y++) {
+ for(y = 0; y < this->bih.biHeight; y++) {
src = sy;
for(x = 0; x < img->width; x++) {
pixel = *src++;
@@ -828,7 +832,7 @@ static void ff_convert_frame(ff_video_decoder_t *this, vo_frame_t *img) {
} else {
- for (y=0; y<img->height; y++) {
+ for (y = 0; y < this->bih.biHeight; y++) {
xine_fast_memcpy (dy, sy, img->width);
dy += img->pitches[0];
@@ -836,7 +840,7 @@ static void ff_convert_frame(ff_video_decoder_t *this, vo_frame_t *img) {
sy += this->av_frame->linesize[0];
}
- for (y=0; y<(img->height/2); y++) {
+ for (y = 0; y < this->bih.biHeight / 2; y++) {
if (this->context->pix_fmt != PIX_FMT_YUV444P) {
diff --git a/src/demuxers/demux_aac.c b/src/demuxers/demux_aac.c
index b8e6ec5c4..68a684ffa 100644
--- a/src/demuxers/demux_aac.c
+++ b/src/demuxers/demux_aac.c
@@ -173,7 +173,7 @@ static int demux_aac_send_chunk(demux_plugin_t *this_gen) {
buf->extra_info->input_time = (8*current_pos) / (bitrate/1000);
bytes_read = this->input->read(this->input, buf->content, buf->max_size);
- if (bytes_read == 0) {
+ if (bytes_read <= 0) {
buf->free_buffer(buf);
this->status = DEMUX_FINISHED;
return this->status;
diff --git a/src/demuxers/demux_ac3.c b/src/demuxers/demux_ac3.c
index 1acb12fcd..711bb0b45 100644
--- a/src/demuxers/demux_ac3.c
+++ b/src/demuxers/demux_ac3.c
@@ -311,13 +311,7 @@ static int demux_ac3_send_chunk (demux_plugin_t *this_gen) {
this->frame_size);
}
- if (buf->size == 0) {
- buf->free_buffer(buf);
- this->status = DEMUX_FINISHED;
- return this->status;
- }
-
- if (buf->size == 0) {
+ if (buf->size <= 0) {
buf->free_buffer(buf);
this->status = DEMUX_FINISHED;
return this->status;
diff --git a/src/demuxers/demux_asf.c b/src/demuxers/demux_asf.c
index 9d4191633..d79782026 100644
--- a/src/demuxers/demux_asf.c
+++ b/src/demuxers/demux_asf.c
@@ -738,7 +738,10 @@ static void asf_send_buffer_nodefrag (demux_asf_t *this, asf_demux_stream_t *str
bufsize = stream->fifo->buffer_pool_buf_size;
buf = stream->fifo->buffer_pool_alloc (stream->fifo);
- this->input->read (this->input, buf->content, bufsize);
+ if (this->input->read (this->input, buf->content, bufsize) != bufsize) {
+ xprintf (this->stream->xine, XINE_VERBOSITY_DEBUG, "demux_asf: input buffer starved\n");
+ return ;
+ }
lprintf ("data: %d %d %d %d\n", buf->content[0], buf->content[1], buf->content[2], buf->content[3]);
@@ -817,7 +820,10 @@ static void asf_send_buffer_defrag (demux_asf_t *this, asf_demux_stream_t *strea
if( stream->frag_offset + frag_len > DEFRAG_BUFSIZE ) {
xprintf (this->stream->xine, XINE_VERBOSITY_DEBUG, "demux_asf: buffer overflow on defrag!\n");
} else {
- this->input->read (this->input, &stream->buffer[stream->frag_offset], frag_len);
+ if (this->input->read (this->input, &stream->buffer[stream->frag_offset], frag_len) != frag_len) {
+ xprintf (this->stream->xine, XINE_VERBOSITY_DEBUG, "demux_asf: input buffer starved\n");
+ return ;
+ }
stream->frag_offset += frag_len;
}
diff --git a/src/demuxers/demux_dts.c b/src/demuxers/demux_dts.c
index 0606586cb..ed1f16d33 100644
--- a/src/demuxers/demux_dts.c
+++ b/src/demuxers/demux_dts.c
@@ -278,7 +278,7 @@ static int demux_dts_send_chunk (demux_plugin_t *this_gen) {
this->frame_size);
}
- if (buf->size == 0) {
+ if (buf->size <= 0) {
buf->free_buffer(buf);
this->status = DEMUX_FINISHED;
return this->status;
diff --git a/src/demuxers/demux_matroska.c b/src/demuxers/demux_matroska.c
index ec75cb97a..086e0cc98 100644
--- a/src/demuxers/demux_matroska.c
+++ b/src/demuxers/demux_matroska.c
@@ -607,6 +607,8 @@ static void init_codec_xiph(demux_matroska_t *this, matroska_track_t *track) {
int i;
uint8_t *data;
+ if (track->codec_private_len < 3)
+ return;
nb_lace = track->codec_private[0];
if (nb_lace != 2)
return;
@@ -614,6 +616,8 @@ static void init_codec_xiph(demux_matroska_t *this, matroska_track_t *track) {
frame[0] = track->codec_private[1];
frame[1] = track->codec_private[2];
frame[2] = track->codec_private_len - frame[0] - frame[1] - 3;
+ if (frame[2] < 0)
+ return;
data = track->codec_private + 3;
for (i = 0; i < 3; i++) {
@@ -1183,7 +1187,12 @@ static int parse_track_entry(demux_matroska_t *this, matroska_track_t *track) {
break;
case MATROSKA_ID_TR_CODECPRIVATE: {
- char *codec_private = malloc (elem.len);
+ char *codec_private;
+ if (elem.len >= 0x80000000)
+ return 0;
+ codec_private = malloc (elem.len);
+ if (! codec_private)
+ return 0;
lprintf("CodecPrivate\n");
if (!ebml_read_binary(ebml, &elem, codec_private)) {
free(codec_private);
@@ -1287,12 +1296,14 @@ static int parse_track_entry(demux_matroska_t *this, matroska_track_t *track) {
if (!strcmp(track->codec_id, MATROSKA_CODEC_ID_V_VFW_FOURCC)) {
xine_bmiheader *bih;
- lprintf("MATROSKA_CODEC_ID_V_VFW_FOURCC\n");
- bih = (xine_bmiheader*)track->codec_private;
- _x_bmiheader_le2me(bih);
+ if (track->codec_private_len >= sizeof(xine_bmiheader)) {
+ lprintf("MATROSKA_CODEC_ID_V_VFW_FOURCC\n");
+ bih = (xine_bmiheader*)track->codec_private;
+ _x_bmiheader_le2me(bih);
- track->buf_type = _x_fourcc_to_buf_video(bih->biCompression);
- init_codec = init_codec_video;
+ track->buf_type = _x_fourcc_to_buf_video(bih->biCompression);
+ init_codec = init_codec_video;
+ }
} else if (!strcmp(track->codec_id, MATROSKA_CODEC_ID_V_UNCOMPRESSED)) {
} else if ((!strcmp(track->codec_id, MATROSKA_CODEC_ID_V_MPEG4_SP)) ||
@@ -1301,6 +1312,9 @@ static int parse_track_entry(demux_matroska_t *this, matroska_track_t *track) {
xine_bmiheader *bih;
lprintf("MATROSKA_CODEC_ID_V_MPEG4_*\n");
+ if (track->codec_private_len > 0x7fffffff - sizeof(xine_bmiheader))
+ track->codec_private_len = 0x7fffffff - sizeof(xine_bmiheader);
+
/* create a bitmap info header struct for MPEG 4 */
bih = calloc(1, sizeof(xine_bmiheader) + track->codec_private_len);
bih->biSize = sizeof(xine_bmiheader) + track->codec_private_len;
@@ -1322,6 +1336,9 @@ static int parse_track_entry(demux_matroska_t *this, matroska_track_t *track) {
xine_bmiheader *bih;
lprintf("MATROSKA_CODEC_ID_V_MPEG4_AVC\n");
+ if (track->codec_private_len > 0x7fffffff - sizeof(xine_bmiheader))
+ track->codec_private_len = 0x7fffffff - sizeof(xine_bmiheader);
+
/* create a bitmap info header struct for h264 */
bih = calloc(1, sizeof(xine_bmiheader) + track->codec_private_len);
bih->biSize = sizeof(xine_bmiheader) + track->codec_private_len;
@@ -1398,11 +1415,13 @@ static int parse_track_entry(demux_matroska_t *this, matroska_track_t *track) {
xine_waveformatex *wfh;
lprintf("MATROSKA_CODEC_ID_A_ACM\n");
- wfh = (xine_waveformatex*)track->codec_private;
- _x_waveformatex_le2me(wfh);
+ if (track->codec_private_len >= sizeof(xine_waveformatex)) {
+ wfh = (xine_waveformatex*)track->codec_private;
+ _x_waveformatex_le2me(wfh);
- track->buf_type = _x_formattag_to_buf_audio(wfh->wFormatTag);
- init_codec = init_codec_audio;
+ track->buf_type = _x_formattag_to_buf_audio(wfh->wFormatTag);
+ init_codec = init_codec_audio;
+ }
} else if (!strncmp(track->codec_id, MATROSKA_CODEC_ID_A_AAC,
sizeof(MATROSKA_CODEC_ID_A_AAC) - 1)) {
lprintf("MATROSKA_CODEC_ID_A_AAC\n");
@@ -1483,9 +1502,14 @@ static int parse_track_entry(demux_matroska_t *this, matroska_track_t *track) {
break;
}
- if (init_codec)
+ if (init_codec) {
+ if (! track->fifo) {
+ xprintf(this->stream->xine, XINE_VERBOSITY_LOG,
+ "demux_matroska: Error: fifo not set up for track of type type %" PRIu32 "\n", track->track_type);
+ return 0;
+ }
init_codec(this, track);
-
+ }
}
}
@@ -1811,6 +1835,11 @@ static int read_block_data (demux_matroska_t *this, size_t len) {
alloc_block_data(this, len);
/* block datas */
+ if (! this->block_data) {
+ xprintf(this->stream->xine, XINE_VERBOSITY_LOG,
+ "demux_matroska: memory allocation error\n");
+ return 0;
+ }
if (this->input->read(this->input, this->block_data, len) != len) {
off_t pos = this->input->get_current_pos(this->input);
xprintf(this->stream->xine, XINE_VERBOSITY_LOG,
diff --git a/src/demuxers/demux_mng.c b/src/demuxers/demux_mng.c
index 0fcdb24ff..d0d83ff80 100644
--- a/src/demuxers/demux_mng.c
+++ b/src/demuxers/demux_mng.c
@@ -104,7 +104,12 @@ static mng_bool mymng_close_stream(mng_handle mngh){
static mng_bool mymng_read_stream(mng_handle mngh, mng_ptr buffer, mng_uint32 size, mng_uint32 *bytesread){
demux_mng_t *this = (demux_mng_t*)mng_get_userdata(mngh);
- *bytesread = this->input->read(this->input, buffer, size);
+ off_t n = this->input->read(this->input, buffer, size);
+ if (n < 0) {
+ *bytesread = 0;
+ return MNG_FALSE;
+ }
+ *bytesread = n;
return MNG_TRUE;
}
@@ -112,6 +117,9 @@ static mng_bool mymng_read_stream(mng_handle mngh, mng_ptr buffer, mng_uint32 si
static mng_bool mymng_process_header(mng_handle mngh, mng_uint32 width, mng_uint32 height){
demux_mng_t *this = (demux_mng_t*)mng_get_userdata(mngh);
+ if (width > 0x8000 || height > 0x8000)
+ return MNG_FALSE;
+
this->bih.biWidth = (width + 7) & ~7;
this->bih.biHeight = height;
this->left_edge = (this->bih.biWidth - width) / 2;
diff --git a/src/demuxers/demux_mod.c b/src/demuxers/demux_mod.c
index bffcf36d8..073927707 100644
--- a/src/demuxers/demux_mod.c
+++ b/src/demuxers/demux_mod.c
@@ -130,9 +130,16 @@ static int probe_mod_file(demux_mod_t *this) {
/* returns 1 if the MOD file was opened successfully, 0 otherwise */
static int open_mod_file(demux_mod_t *this) {
int total_read;
+ off_t input_length;
/* Get size and create buffer */
- this->filesize = this->input->get_length(this->input);
+ input_length = this->input->get_length(this->input);
+ /* Avoid potential issues with signed variables and e.g. read() returning -1 */
+ if (input_length > 0x7FFFFFFF || input_length < 0) {
+ xine_log(this->stream->xine, XINE_LOG_PLUGIN, "modplug - size overflow\n");
+ return 0;
+ }
+ this->filesize = input_length;
this->buffer = (char *)malloc(this->filesize);
if(!this->buffer) {
xine_log(this->stream->xine, XINE_LOG_PLUGIN, "modplug - allocation failure\n");
diff --git a/src/demuxers/demux_mpc.c b/src/demuxers/demux_mpc.c
index 9b27e5954..220e1b8b6 100644
--- a/src/demuxers/demux_mpc.c
+++ b/src/demuxers/demux_mpc.c
@@ -209,7 +209,7 @@ static int demux_mpc_send_chunk(demux_plugin_t *this_gen) {
/* Read data */
bytes_read = this->input->read(this->input, buf->content, bytes_to_read);
- if(bytes_read == 0) {
+ if(bytes_read <= 0) {
buf->free_buffer(buf);
this->status = DEMUX_FINISHED;
return this->status;
diff --git a/src/demuxers/demux_mpeg.c b/src/demuxers/demux_mpeg.c
index fa167c70e..85b62f48e 100644
--- a/src/demuxers/demux_mpeg.c
+++ b/src/demuxers/demux_mpeg.c
@@ -279,6 +279,10 @@ static void parse_mpeg2_packet (demux_mpeg_t *this, int stream_id, int64_t scr)
if((this->dummy_space[0] & 0xE0) == 0x20) {
buf = this->input->read_block (this->input, this->video_fifo, len-1);
+ if (! buf) {
+ this->status = DEMUX_FINISHED;
+ return;
+ }
track = (this->dummy_space[0] & 0x1f);
@@ -298,6 +302,10 @@ static void parse_mpeg2_packet (demux_mpeg_t *this, int stream_id, int64_t scr)
int spu_id = this->dummy_space[1] & 0x03;
buf = this->input->read_block (this->input, this->video_fifo, len-1);
+ if (! buf) {
+ this->status = DEMUX_FINISHED;
+ return;
+ }
buf->type = BUF_SPU_SVCD + spu_id;
buf->pts = pts;
@@ -318,6 +326,10 @@ static void parse_mpeg2_packet (demux_mpeg_t *this, int stream_id, int64_t scr)
if((this->dummy_space[0] & 0xfc) == 0x00) {
buf = this->input->read_block (this->input, this->video_fifo, len-1);
+ if (! buf) {
+ this->status = DEMUX_FINISHED;
+ return;
+ }
buf->type = BUF_SPU_CVD + (this->dummy_space[0] & 0x03);
buf->pts = pts;
@@ -376,6 +388,10 @@ static void parse_mpeg2_packet (demux_mpeg_t *this, int stream_id, int64_t scr)
i = this->input->read (this->input, this->dummy_space+1, 6);
buf = this->input->read_block (this->input, this->video_fifo, len-7);
+ if (! buf) {
+ this->status = DEMUX_FINISHED;
+ return;
+ }
buf->type = BUF_AUDIO_LPCM_BE + track;
buf->decoder_flags |= BUF_FLAG_SPECIAL;
@@ -920,7 +936,7 @@ static void demux_mpeg_resync (demux_mpeg_t *this, uint32_t buf) {
if (pos == len) {
len = this->input->read(this->input, dummy_buf, sizeof(dummy_buf));
pos = 0;
- if (len == 0) {
+ if (len <= 0) {
this->status = DEMUX_FINISHED;
break;
}
diff --git a/src/demuxers/demux_mpeg_block.c b/src/demuxers/demux_mpeg_block.c
index 3ecb88d04..4fa96faeb 100644
--- a/src/demuxers/demux_mpeg_block.c
+++ b/src/demuxers/demux_mpeg_block.c
@@ -1190,14 +1190,14 @@ static int demux_mpeg_detect_blocksize(demux_mpeg_block_t *this,
input_plugin_t *input)
{
input->seek(input, 2048, SEEK_SET);
- if (!input->read(input, this->scratch, 4))
+ if (input->read(input, this->scratch, 4) != 4)
return 0;
if (this->scratch[0] || this->scratch[1]
|| (this->scratch[2] != 0x01) || (this->scratch[3] != 0xba)) {
input->seek(input, 2324, SEEK_SET);
- if (!input->read(input, this->scratch, 4))
+ if (input->read(input, this->scratch, 4) != 4)
return 0;
if (this->scratch[0] || this->scratch[1]
|| (this->scratch[2] != 0x01) || (this->scratch[3] != 0xba))
@@ -1417,7 +1417,7 @@ static demux_plugin_t *open_plugin (demux_class_t *class_gen, xine_stream_t *str
}
input->seek(input, 0, SEEK_SET);
- if (input->read(input, this->scratch, this->blocksize)) {
+ if (input->read(input, this->scratch, this->blocksize) == this->blocksize) {
lprintf("open_plugin:read worked\n");
if (this->scratch[0] || this->scratch[1]
diff --git a/src/demuxers/demux_mpeg_pes.c b/src/demuxers/demux_mpeg_pes.c
index d9ac952d8..b7c0e7e6d 100644
--- a/src/demuxers/demux_mpeg_pes.c
+++ b/src/demuxers/demux_mpeg_pes.c
@@ -1686,7 +1686,7 @@ static demux_plugin_t *open_plugin (demux_class_t *class_gen, xine_stream_t *str
if (((input->get_capabilities(input) & INPUT_CAP_SEEKABLE) != 0) ) {
input->seek(input, 0, SEEK_SET);
- if (input->read(input, (char *)this->scratch, 6)) {
+ if (input->read(input, (char *)this->scratch, 6) == 6) {
lprintf("open_plugin:read worked\n");
if (this->scratch[0] || this->scratch[1]
diff --git a/src/demuxers/demux_nsf.c b/src/demuxers/demux_nsf.c
index 60d5049d9..926ea97e1 100644
--- a/src/demuxers/demux_nsf.c
+++ b/src/demuxers/demux_nsf.c
@@ -124,7 +124,7 @@ static int demux_nsf_send_chunk(demux_plugin_t *this_gen) {
buf->type = BUF_AUDIO_NSF;
bytes_read = this->input->read(this->input, buf->content, buf->max_size);
- if (bytes_read == 0) {
+ if (bytes_read <= 0) {
/* the file has been completely loaded, free the buffer and start
* sending control buffers */
buf->free_buffer(buf);
diff --git a/src/demuxers/demux_ogg.c b/src/demuxers/demux_ogg.c
index 9e9de45aa..e3a9b20c4 100644
--- a/src/demuxers/demux_ogg.c
+++ b/src/demuxers/demux_ogg.c
@@ -237,7 +237,7 @@ static int read_ogg_packet (demux_ogg_t *this) {
while (ogg_sync_pageout(&this->oy,&this->og)!=1) {
buffer = ogg_sync_buffer(&this->oy, CHUNKSIZE);
bytes = this->input->read(this->input, buffer, CHUNKSIZE);
- if (bytes == 0) {
+ if (bytes <= 0) {
if (total == 0) {
lprintf("read_ogg_packet read nothing\n");
return 0;
diff --git a/src/demuxers/demux_qt.c b/src/demuxers/demux_qt.c
index 1fa9b4327..4ad71e958 100644
--- a/src/demuxers/demux_qt.c
+++ b/src/demuxers/demux_qt.c
@@ -738,6 +738,8 @@ static void parse_meta_atom(qt_info *info, unsigned char *meta_atom) {
if (current_atom == ART_ATOM) {
string_size = _X_BE_32(&meta_atom[i + 4]) - 16 + 1;
+ if (string_size <= 0)
+ continue;
info->artist = xine_xmalloc(string_size);
if (info->artist) {
strncpy(info->artist, &meta_atom[i + 20], string_size - 1);
@@ -745,6 +747,8 @@ static void parse_meta_atom(qt_info *info, unsigned char *meta_atom) {
}
} else if (current_atom == NAM_ATOM) {
string_size = _X_BE_32(&meta_atom[i + 4]) - 16 + 1;
+ if (string_size <= 0)
+ continue;
info->name = xine_xmalloc(string_size);
if (info->name) {
strncpy(info->name, &meta_atom[i + 20], string_size - 1);
@@ -752,6 +756,8 @@ static void parse_meta_atom(qt_info *info, unsigned char *meta_atom) {
}
} else if (current_atom == ALB_ATOM) {
string_size = _X_BE_32(&meta_atom[i + 4]) - 16 + 1;
+ if (string_size <= 0)
+ continue;
info->album = xine_xmalloc(string_size);
if (info->album) {
strncpy(info->album, &meta_atom[i + 20], string_size - 1);
@@ -759,6 +765,8 @@ static void parse_meta_atom(qt_info *info, unsigned char *meta_atom) {
}
} else if (current_atom == GEN_ATOM) {
string_size = _X_BE_32(&meta_atom[i + 4]) - 16 + 1;
+ if (string_size <= 0)
+ continue;
info->genre = xine_xmalloc(string_size);
if (info->genre) {
strncpy(info->genre, &meta_atom[i + 20], string_size - 1);
@@ -766,6 +774,8 @@ static void parse_meta_atom(qt_info *info, unsigned char *meta_atom) {
}
} else if (current_atom == TOO_ATOM) {
string_size = _X_BE_32(&meta_atom[i + 4]) - 16 + 1;
+ if (string_size <= 0)
+ continue;
info->comment = xine_xmalloc(string_size);
if (info->comment) {
strncpy(info->comment, &meta_atom[i + 20], string_size - 1);
@@ -773,6 +783,8 @@ static void parse_meta_atom(qt_info *info, unsigned char *meta_atom) {
}
} else if (current_atom == WRT_ATOM) {
string_size = _X_BE_32(&meta_atom[i + 4]) - 16 + 1;
+ if (string_size <= 0)
+ continue;
info->composer = xine_xmalloc(string_size);
if (info->composer) {
strncpy(info->composer, &meta_atom[i + 20], string_size - 1);
@@ -780,6 +792,8 @@ static void parse_meta_atom(qt_info *info, unsigned char *meta_atom) {
}
} else if (current_atom == DAY_ATOM) {
string_size = _X_BE_32(&meta_atom[i + 4]) - 16 + 1;
+ if (string_size <= 0)
+ continue;
info->year = xine_xmalloc(string_size);
if (info->year) {
strncpy(info->year, &meta_atom[i + 20], string_size - 1);
@@ -947,6 +961,10 @@ static qt_error parse_trak_atom (qt_trak *trak,
/* allocate space for each of the properties unions */
trak->stsd_atoms_count = _X_BE_32(&trak_atom[i + 8]);
+ if (trak->stsd_atoms_count <= 0) {
+ last_error = QT_HEADER_TROUBLE;
+ goto free_trak;
+ }
trak->stsd_atoms = calloc(trak->stsd_atoms_count, sizeof(properties_t));
if (!trak->stsd_atoms) {
last_error = QT_NO_MEMORY;
@@ -958,6 +976,10 @@ static qt_error parse_trak_atom (qt_trak *trak,
for (k = 0; k < trak->stsd_atoms_count; k++) {
current_stsd_atom_size = _X_BE_32(&trak_atom[atom_pos - 4]);
+ if (current_stsd_atom_size < 4) {
+ last_error = QT_HEADER_TROUBLE;
+ goto free_trak;
+ }
if (trak->type == MEDIA_VIDEO) {
@@ -1575,13 +1597,16 @@ static qt_error parse_reference_atom (reference_t *ref,
qt_atom current_atom;
unsigned int current_atom_size;
+ if (ref_atom_size >= 0x80000000)
+ return QT_NOT_A_VALID_FILE;
+
/* initialize reference atom */
ref->url = NULL;
ref->data_rate = 0;
ref->qtim_version = 0;
/* traverse through the atom looking for the key atoms */
- for (i = ATOM_PREAMBLE_SIZE; i < ref_atom_size - 4; i++) {
+ for (i = ATOM_PREAMBLE_SIZE; i + 4 < ref_atom_size; i++) {
current_atom_size = _X_BE_32(&ref_atom[i - 4]);
current_atom = _X_BE_32(&ref_atom[i]);
@@ -1590,7 +1615,7 @@ static qt_error parse_reference_atom (reference_t *ref,
size_t string_size = _X_BE_32(&ref_atom[i + 12]);
size_t url_offset = 0;
- if (string_size >= current_atom_size || i + string_size >= ref_atom_size)
+ if (string_size >= current_atom_size || string_size >= ref_atom_size - i)
return QT_NOT_A_VALID_FILE;
/* if the URL starts with "http://", copy it */
@@ -1598,6 +1623,8 @@ static qt_error parse_reference_atom (reference_t *ref,
memcmp(&ref_atom[i + 16], "rtsp://", 7) &&
base_mrl )
url_offset = strlen(base_mrl);
+ if (url_offset >= 0x80000000)
+ return QT_NOT_A_VALID_FILE;
/* otherwise, append relative URL to base MRL */
string_size += url_offset;
@@ -2181,7 +2208,7 @@ static qt_error open_qt_file(qt_info *info, input_plugin_t *input,
}
/* check if moov is compressed */
- if (_X_BE_32(&moov_atom[12]) == CMOV_ATOM) {
+ if (_X_BE_32(&moov_atom[12]) == CMOV_ATOM && moov_atom_size >= 0x28) {
info->compressed_header = 1;
diff --git a/src/demuxers/demux_real.c b/src/demuxers/demux_real.c
index aa4dfc26b..0df9a426e 100644
--- a/src/demuxers/demux_real.c
+++ b/src/demuxers/demux_real.c
@@ -318,9 +318,15 @@ static void real_free_mdpr (mdpr_t *mdpr) {
}
static void real_parse_audio_specific_data (demux_real_t *this,
- real_stream_t * stream,
- uint8_t * data)
+ real_stream_t * stream)
{
+ if (stream->mdpr->type_specific_len < 46) {
+ xprintf (this->stream->xine, XINE_VERBOSITY_LOG,
+ "demux_real: audio data size smaller than header length!\n");
+ return;
+ }
+
+ uint8_t * data = stream->mdpr->type_specific_data;
const uint32_t coded_frame_size = _X_BE_32 (data+24);
const uint16_t codec_data_length = _X_BE_16 (data+40);
const uint16_t coded_frame_size2 = _X_BE_16 (data+42);
@@ -359,9 +365,14 @@ static void real_parse_audio_specific_data (demux_real_t *this,
* stream->frame_size = stream->w / stream->sps * stream->h * stream->sps;
* but it looks pointless? the compiler will probably optimise it away, I suppose?
*/
- stream->frame_size = stream->w * stream->h;
+ if (stream->w < 32768 && stream->h < 32768) {
+ stream->frame_size = stream->w * stream->h;
+ stream->frame_buffer = calloc(stream->frame_size, 1);
+ } else {
+ stream->frame_size = 0;
+ stream->frame_buffer = NULL;
+ }
- stream->frame_buffer = calloc(stream->frame_size, 1);
stream->frame_num_bytes = 0;
stream->sub_packet_cnt = 0;
@@ -430,9 +441,14 @@ static void real_parse_headers (demux_real_t *this) {
case MDPR_TAG:
case CONT_TAG:
{
+ if (chunk_size < PREAMBLE_SIZE+1) {
+ this->status = DEMUX_FINISHED;
+ return;
+ }
chunk_size -= PREAMBLE_SIZE;
uint8_t *const chunk_buffer = malloc(chunk_size);
- if (this->input->read(this->input, chunk_buffer, chunk_size) !=
+ if (! chunk_buffer ||
+ this->input->read(this->input, chunk_buffer, chunk_size) !=
chunk_size) {
free (chunk_buffer);
this->status = DEMUX_FINISHED;
@@ -487,7 +503,8 @@ static void real_parse_headers (demux_real_t *this) {
this->audio_streams[this->num_audio_streams].index = NULL;
this->audio_streams[this->num_audio_streams].mdpr = mdpr;
this->num_audio_streams++;
- } else if(_X_BE_32(mdpr->type_specific_data) == RA_TAG) {
+ } else if(_X_BE_32(mdpr->type_specific_data) == RA_TAG &&
+ mdpr->type_specific_len >= 6) {
if(this->num_audio_streams == MAX_AUDIO_STREAMS) {
xprintf(this->stream->xine, XINE_VERBOSITY_DEBUG,
"demux_real: maximum number of audio stream exceeded\n");
@@ -498,26 +515,30 @@ static void real_parse_headers (demux_real_t *this) {
lprintf("audio version %d detected\n", version);
- char *fourcc_ptr = NULL;
+ char *fourcc_ptr = "\0\0\0";
switch(version) {
case 3:
/* Version 3 header stores fourcc after meta info - cheat by reading backwards from the
* end of the header instead of having to parse it all */
- fourcc_ptr = mdpr->type_specific_data + mdpr->type_specific_len - 5;
+ if (mdpr->type_specific_len >= 5)
+ fourcc_ptr = mdpr->type_specific_data + mdpr->type_specific_len - 5;
break;
case 4: {
- const uint8_t len = *(mdpr->type_specific_data + 56);
- fourcc_ptr = mdpr->type_specific_data + 58 + len;
+ if (mdpr->type_specific_len >= 57) {
+ const uint8_t len = *(mdpr->type_specific_data + 56);
+ if (mdpr->type_specific_len >= 62 + len)
+ fourcc_ptr = mdpr->type_specific_data + 58 + len;
+ }
}
break;
case 5:
- fourcc_ptr = mdpr->type_specific_data + 66;
+ if (mdpr->type_specific_len >= 70)
+ fourcc_ptr = mdpr->type_specific_data + 66;
break;
default:
lprintf("unsupported audio header version %d\n", version);
goto unknown;
}
-
lprintf("fourcc = %.4s\n", fourcc_ptr);
const uint32_t fourcc = _X_ME_32(fourcc_ptr);
@@ -528,11 +549,11 @@ static void real_parse_headers (demux_real_t *this) {
this->audio_streams[this->num_audio_streams].mdpr = mdpr;
real_parse_audio_specific_data (this,
- &this->audio_streams[this->num_audio_streams],
- mdpr->type_specific_data);
+ &this->audio_streams[this->num_audio_streams]);
this->num_audio_streams++;
- } else if(_X_BE_32(mdpr->type_specific_data + 4) == VIDO_TAG) {
+ } else if(_X_BE_32(mdpr->type_specific_data + 4) == VIDO_TAG &&
+ mdpr->type_specific_len >= 34) {
if(this->num_video_streams == MAX_VIDEO_STREAMS) {
xprintf(this->stream->xine, XINE_VERBOSITY_DEBUG,
diff --git a/src/demuxers/demux_realaudio.c b/src/demuxers/demux_realaudio.c
index 1c39c6208..44449667c 100644
--- a/src/demuxers/demux_realaudio.c
+++ b/src/demuxers/demux_realaudio.c
@@ -202,11 +202,19 @@ static int open_ra_file(demux_ra_t *this) {
this->h = _X_BE_16 (this->header+40);
this->cfs = _X_BE_32 (this->header+24);
- this->frame_len = this->w * this->h;
- this->frame_size = this->frame_len * sps;
-
- this->frame_buffer = calloc(this->frame_size, 1);
- _x_assert(this->frame_buffer != NULL);
+ if (this->w < 0x8000 && this->h < 0x8000) {
+ uint64_t fs;
+ this->frame_len = this->w * this->h;
+ fs = (uint64_t) this->frame_len * sps;
+ if (fs < 0x80000000) {
+ this->frame_size = fs;
+ this->frame_buffer = calloc(this->frame_size, 1);
+ }
+ }
+ if (! this->frame_buffer) {
+ xprintf(this->stream->xine, XINE_VERBOSITY_DEBUG, "demux_realaudio: malloc failed\n");
+ return 0;
+ }
if (this->audio_type == BUF_AUDIO_28_8 || this->audio_type == BUF_AUDIO_SIPRO)
this->block_align = this->cfs;
diff --git a/src/demuxers/demux_shn.c b/src/demuxers/demux_shn.c
index 4d932305c..ccc34b57f 100644
--- a/src/demuxers/demux_shn.c
+++ b/src/demuxers/demux_shn.c
@@ -88,7 +88,7 @@ static int demux_shn_send_chunk(demux_plugin_t *this_gen) {
buf->pts = 0;
bytes_read = this->input->read(this->input, buf->content, buf->max_size);
- if (bytes_read == 0) {
+ if (bytes_read <= 0) {
buf->free_buffer(buf);
this->status = DEMUX_FINISHED;
return this->status;
diff --git a/src/demuxers/demux_slave.c b/src/demuxers/demux_slave.c
index 28a89a973..abb4d01e5 100644
--- a/src/demuxers/demux_slave.c
+++ b/src/demuxers/demux_slave.c
@@ -90,10 +90,11 @@ static int demux_slave_next (demux_slave_t *this) {
/* fill the scratch buffer */
n = this->input->read(this->input, &this->scratch[this->scratch_used],
SCRATCH_SIZE - this->scratch_used);
- this->scratch_used += n;
+ if (n > 0)
+ this->scratch_used += n;
this->scratch[this->scratch_used] = '\0';
- if( !n ) {
+ if (n <= 0) {
lprintf("connection closed\n");
this->status = DEMUX_FINISHED;
return 0;
diff --git a/src/demuxers/demux_ts.c b/src/demuxers/demux_ts.c
index 55e06c033..98de1f9ea 100644
--- a/src/demuxers/demux_ts.c
+++ b/src/demuxers/demux_ts.c
@@ -1576,7 +1576,7 @@ static unsigned char * demux_synchronise(demux_ts_t* this) {
do {
read_length = this->input->read(this->input, this->buf,
PKT_SIZE * NPKT_PER_READ);
- if (read_length % PKT_SIZE) {
+ if (read_length < 0 || read_length % PKT_SIZE) {
xprintf (this->stream->xine, XINE_VERBOSITY_DEBUG,
"demux_ts: read returned %d bytes (not a multiple of %d!)\n",
read_length, PKT_SIZE);
diff --git a/src/demuxers/demux_tta.c b/src/demuxers/demux_tta.c
index 68305a444..de50ac63d 100644
--- a/src/demuxers/demux_tta.c
+++ b/src/demuxers/demux_tta.c
@@ -126,6 +126,10 @@ static int demux_tta_send_chunk(demux_plugin_t *this_gen) {
/* buf->extra_info->input_time = this->current_sample / this->samplerate; */
bytes_read = this->input->read(this->input, buf->content, ( bytes_to_read > buf->max_size ) ? buf->max_size : bytes_to_read);
+ if (bytes_read < 0) {
+ this->status = DEMUX_FINISHED;
+ break;
+ }
buf->size = bytes_read;
diff --git a/src/demuxers/demux_vox.c b/src/demuxers/demux_vox.c
index d646a756f..1b34106ad 100644
--- a/src/demuxers/demux_vox.c
+++ b/src/demuxers/demux_vox.c
@@ -77,7 +77,7 @@ static int demux_vox_send_chunk (demux_plugin_t *this_gen) {
buf = this->audio_fifo->buffer_pool_alloc (this->audio_fifo);
buf->type = BUF_AUDIO_DIALOGIC_IMA;
bytes_read = this->input->read(this->input, buf->content, buf->max_size);
- if (bytes_read == 0) {
+ if (bytes_read <= 0) {
buf->free_buffer(buf);
this->status = DEMUX_FINISHED;
return this->status;
diff --git a/src/demuxers/demux_yuv_frames.c b/src/demuxers/demux_yuv_frames.c
index c5ca363ed..089207f58 100644
--- a/src/demuxers/demux_yuv_frames.c
+++ b/src/demuxers/demux_yuv_frames.c
@@ -126,13 +126,19 @@ static void demux_yuv_frames_send_headers (demux_plugin_t *this_gen){
if(_x_stream_info_get(this->stream, XINE_STREAM_INFO_HAS_AUDIO)) {
buf = this->input->read_block(this->input, this->audio_fifo, 0);
- this->audio_fifo->put(this->audio_fifo, buf);
+ if (buf)
+ this->audio_fifo->put(this->audio_fifo, buf);
+ else
+ this->status = DEMUX_FINISHED;
}
if(_x_stream_info_get(this->stream, XINE_STREAM_INFO_HAS_VIDEO)) {
buf = this->input->read_block(this->input, this->video_fifo, 0);
- this->video_fifo->put(this->video_fifo, buf);
+ if (buf)
+ this->video_fifo->put(this->video_fifo, buf);
+ else
+ this->status = DEMUX_FINISHED;
}
this->status = DEMUX_OK;
diff --git a/src/input/input_dvb.c b/src/input/input_dvb.c
index d4f4c342f..4a1e71a38 100644
--- a/src/input/input_dvb.c
+++ b/src/input/input_dvb.c
@@ -2602,6 +2602,10 @@ static buf_element_t *dvb_plugin_read_block (input_plugin_t *this_gen,
buf_element_t *buf = fifo->buffer_pool_alloc (fifo);
int total_bytes;
+ if (todo < 0 || todo > buf->size) {
+ buf->free_buffer (buf);
+ return NULL;
+ }
buf->content = buf->mem;
buf->type = BUF_DEMUX_BLOCK;
diff --git a/src/input/input_dvd.c b/src/input/input_dvd.c
index a845d7628..ff3000e5d 100644
--- a/src/input/input_dvd.c
+++ b/src/input/input_dvd.c
@@ -850,6 +850,9 @@ static buf_element_t *dvd_plugin_read_block (input_plugin_t *this_gen,
static off_t dvd_plugin_read (input_plugin_t *this_gen, char *ch_buf, off_t len) {
/* dvd_input_plugin_t *this = (dvd_input_plugin_t*)this_gen; */
+ if (len < 4)
+ return -1;
+
/* FIXME: Tricking the demux_mpeg_block plugin */
ch_buf[0] = 0;
ch_buf[1] = 0;
diff --git a/src/input/input_file.c b/src/input/input_file.c
index 774f6b081..690913aa4 100644
--- a/src/input/input_file.c
+++ b/src/input/input_file.c
@@ -145,6 +145,9 @@ static int check_mmap_file(file_input_plugin_t *this) {
static off_t file_plugin_read (input_plugin_t *this_gen, char *buf, off_t len) {
file_input_plugin_t *this = (file_input_plugin_t *) this_gen;
+ if (len < 0)
+ return -1;
+
#ifdef HAVE_MMAP
if ( check_mmap_file(this) ) {
off_t l = len;
@@ -166,6 +169,11 @@ static buf_element_t *file_plugin_read_block (input_plugin_t *this_gen, fifo_buf
file_input_plugin_t *this = (file_input_plugin_t *) this_gen;
buf_element_t *buf = fifo->buffer_pool_alloc (fifo);
+ if (todo < 0 || todo > buf->size) {
+ buf->free_buffer (buf);
+ return NULL;
+ }
+
buf->type = BUF_DEMUX_BLOCK;
#ifdef HAVE_MMAP
diff --git a/src/input/input_gnome_vfs.c b/src/input/input_gnome_vfs.c
index 0848b9206..ec025f7b5 100644
--- a/src/input/input_gnome_vfs.c
+++ b/src/input/input_gnome_vfs.c
@@ -121,6 +121,11 @@ gnomevfs_plugin_read_block (input_plugin_t *this_gen, fifo_buffer_t *fifo,
off_t total_bytes;
buf_element_t *buf = fifo->buffer_pool_alloc (fifo);
+ if (todo < 0 || todo > buf->size) {
+ buf->free_buffer (buf);
+ return NULL;
+ }
+
buf->content = buf->mem;
buf->type = BUF_DEMUX_BLOCK;
diff --git a/src/input/input_http.c b/src/input/input_http.c
index 169a0d384..3cb745656 100644
--- a/src/input/input_http.c
+++ b/src/input/input_http.c
@@ -421,6 +421,9 @@ static off_t http_plugin_read (input_plugin_t *this_gen,
num_bytes = 0;
+ if (nlen < 0)
+ return -1;
+
if (this->curpos < this->preview_size) {
if (nlen > (this->preview_size - this->curpos))
@@ -437,7 +440,7 @@ static off_t http_plugin_read (input_plugin_t *this_gen,
n = nlen - num_bytes;
- if (n) {
+ if (n > 0) {
int read_bytes;
read_bytes = http_plugin_read_int (this, &buf[num_bytes], n);
@@ -503,6 +506,11 @@ static buf_element_t *http_plugin_read_block (input_plugin_t *this_gen, fifo_buf
off_t total_bytes;
buf_element_t *buf = fifo->buffer_pool_alloc (fifo);
+ if (todo < 0 || todo > buf->size) {
+ buf->free_buffer (buf);
+ return NULL;
+ }
+
buf->content = buf->mem;
buf->type = BUF_DEMUX_BLOCK;
@@ -554,7 +562,7 @@ static off_t http_plugin_seek(input_plugin_t *this_gen, off_t offset, int origin
if ((origin == SEEK_CUR) && (offset >= 0)) {
for (;((int)offset) - BUFSIZE > 0; offset -= BUFSIZE) {
- if( !this_gen->read (this_gen, this->seek_buf, BUFSIZE) )
+ if( this_gen->read (this_gen, this->seek_buf, BUFSIZE) <= 0 )
return this->curpos;
}
@@ -576,7 +584,7 @@ static off_t http_plugin_seek(input_plugin_t *this_gen, off_t offset, int origin
offset -= this->curpos;
for (;((int)offset) - BUFSIZE > 0; offset -= BUFSIZE) {
- if( !this_gen->read (this_gen, this->seek_buf, BUFSIZE) )
+ if( this_gen->read (this_gen, this->seek_buf, BUFSIZE) <= 0 )
return this->curpos;
}
@@ -996,6 +1004,7 @@ static int http_plugin_open (input_plugin_t *this_gen ) {
this->preview_size = http_plugin_read_int (this, this->preview, MAX_PREVIEW_SIZE);
}
if (this->preview_size < 0) {
+ this->preview_size = 0;
xine_log (this->stream->xine, XINE_LOG_MSG, _("input_http: read error %d\n"), errno);
return -12;
}
diff --git a/src/input/input_mms.c b/src/input/input_mms.c
index 158b40448..d5cc0a2ac 100644
--- a/src/input/input_mms.c
+++ b/src/input/input_mms.c
@@ -122,6 +122,11 @@ static buf_element_t *mms_plugin_read_block (input_plugin_t *this_gen,
lprintf ("mms_plugin_read_block: %"PRId64" bytes...\n", todo);
+ if (todo < 0 || todo > buf->size) {
+ buf->free_buffer (buf);
+ return NULL;
+ }
+
buf->content = buf->mem;
buf->type = BUF_DEMUX_BLOCK;
diff --git a/src/input/input_net.c b/src/input/input_net.c
index 391f33a60..719203ff9 100644
--- a/src/input/input_net.c
+++ b/src/input/input_net.c
@@ -253,6 +253,9 @@ static off_t net_plugin_read (input_plugin_t *this_gen,
lprintf("reading %" PRIdMAX " bytes...\n", (intmax_t)len);
+ if (len < 0)
+ return -1;
+
total=0;
if (this->curpos < this->preview_size) {
n = this->preview_size - this->curpos;
@@ -288,6 +291,11 @@ static buf_element_t *net_plugin_read_block (input_plugin_t *this_gen,
buf_element_t *buf = fifo->buffer_pool_alloc (fifo);
off_t total_bytes;
+ if (todo < 0 || todo > buf->size) {
+ buf->free_buffer (buf);
+ return NULL;
+ }
+
buf->content = buf->mem;
buf->type = BUF_DEMUX_BLOCK;
@@ -331,7 +339,7 @@ static off_t net_plugin_seek (input_plugin_t *this_gen, off_t offset, int origin
if ((origin == SEEK_CUR) && (offset >= 0)) {
for (;((int)offset) - BUFSIZE > 0; offset -= BUFSIZE) {
- if( !this_gen->read (this_gen, this->seek_buf, BUFSIZE) )
+ if( this_gen->read (this_gen, this->seek_buf, BUFSIZE) <= 0 )
return this->curpos;
}
@@ -353,7 +361,7 @@ static off_t net_plugin_seek (input_plugin_t *this_gen, off_t offset, int origin
offset -= this->curpos;
for (;((int)offset) - BUFSIZE > 0; offset -= BUFSIZE) {
- if( !this_gen->read (this_gen, this->seek_buf, BUFSIZE) )
+ if( this_gen->read (this_gen, this->seek_buf, BUFSIZE) <= 0 )
return this->curpos;
}
diff --git a/src/input/input_pnm.c b/src/input/input_pnm.c
index 669d24d28..af2b8add2 100644
--- a/src/input/input_pnm.c
+++ b/src/input/input_pnm.c
@@ -83,7 +83,8 @@ static off_t pnm_plugin_read (input_plugin_t *this_gen,
lprintf ("pnm_plugin_read: %"PRId64" bytes ...\n", len);
n = pnm_read (this->pnm, buf, len);
- this->curpos += n;
+ if (n >= 0)
+ this->curpos += n;
return n;
}
@@ -96,6 +97,11 @@ static buf_element_t *pnm_plugin_read_block (input_plugin_t *this_gen,
lprintf ("pnm_plugin_read_block: %"PRId64" bytes...\n", todo);
+ if (todo < 0 || todo > buf->size) {
+ buf->free_buffer (buf);
+ return NULL;
+ }
+
buf->content = buf->mem;
buf->type = BUF_DEMUX_BLOCK;
@@ -123,10 +129,16 @@ static off_t pnm_plugin_seek (input_plugin_t *this_gen, off_t offset, int origin
if ((origin == SEEK_CUR) && (offset >= 0)) {
for (;((int)offset) - BUFSIZE > 0; offset -= BUFSIZE) {
- this->curpos += pnm_plugin_read (this_gen, this->scratch, BUFSIZE);
+ off_t n = pnm_plugin_read (this_gen, this->scratch, BUFSIZE);
+ if (n <= 0)
+ return this->curpos;
+ this->curpos += n;
}
- this->curpos += pnm_plugin_read (this_gen, this->scratch, offset);
+ off_t n = pnm_plugin_read (this_gen, this->scratch, offset);
+ if (n <= 0)
+ return this->curpos;
+ this->curpos += n;
}
return this->curpos;
diff --git a/src/input/input_pvr.c b/src/input/input_pvr.c
index 009c76939..18d29f6be 100644
--- a/src/input/input_pvr.c
+++ b/src/input/input_pvr.c
@@ -424,6 +424,9 @@ static uint32_t pvr_plugin_get_capabilities (input_plugin_t *this_gen) {
static off_t pvr_plugin_read (input_plugin_t *this_gen, char *buf, off_t len) {
/*pvr_input_plugin_t *this = (pvr_input_plugin_t *) this_gen;*/
+ if (len < 4)
+ return -1;
+
/* FIXME: Tricking the demux_mpeg_block plugin */
buf[0] = 0;
buf[1] = 0;
@@ -1199,6 +1202,9 @@ static buf_element_t *pvr_plugin_read_block (input_plugin_t *this_gen, fifo_buff
buf_element_t *buf;
int speed = _x_get_speed(this->stream);
+ if (todo < 0 || todo > buf->size)
+ return NULL;
+
if( !this->pvr_running ) {
xprintf(this->stream->xine, XINE_VERBOSITY_DEBUG, "input_pvr: thread died, aborting\n");
return NULL;
diff --git a/src/input/input_rtp.c b/src/input/input_rtp.c
index 66fcba87e..8d07eb6cf 100644
--- a/src/input/input_rtp.c
+++ b/src/input/input_rtp.c
@@ -453,6 +453,9 @@ static off_t rtp_plugin_read (input_plugin_t *this_gen,
struct timespec timeout;
off_t copied = 0;
+ if (length < 0)
+ return -1;
+
while(length > 0) {
off_t n;
@@ -524,6 +527,10 @@ static buf_element_t *rtp_plugin_read_block (input_plugin_t *this_gen,
buf_element_t *buf = fifo->buffer_pool_alloc (fifo);
int total_bytes;
+ if (todo < 0 || todo > buf->size) {
+ buf->free_buffer (buf);
+ return NULL;
+ }
buf->content = buf->mem;
buf->type = BUF_DEMUX_BLOCK;
@@ -609,11 +616,14 @@ static int rtp_plugin_get_optional_data (input_plugin_t *this_gen,
if (data_type == INPUT_OPTIONAL_DATA_PREVIEW) {
if (!this->preview_read_done) {
this->preview_size = rtp_plugin_read(this_gen, this->preview, MAX_PREVIEW_SIZE);
+ if (this->preview_size < 0)
+ this->preview_size = 0;
lprintf("Preview data length = %d\n", this->preview_size);
this->preview_read_done = 1;
}
- memcpy(data, this->preview, this->preview_size);
+ if (this->preview_size)
+ memcpy(data, this->preview, this->preview_size);
return this->preview_size;
}
else {
diff --git a/src/input/input_rtsp.c b/src/input/input_rtsp.c
index 110c4d4b6..bfe8fdf85 100644
--- a/src/input/input_rtsp.c
+++ b/src/input/input_rtsp.c
@@ -84,7 +84,8 @@ static off_t rtsp_plugin_read (input_plugin_t *this_gen,
lprintf ("rtsp_plugin_read: %"PRId64" bytes ...\n", len);
n = rtsp_session_read (this->rtsp, buf, len);
- this->curpos += n;
+ if (n > 0)
+ this->curpos += n;
return n;
}
@@ -97,6 +98,11 @@ static buf_element_t *rtsp_plugin_read_block (input_plugin_t *this_gen,
lprintf ("rtsp_plugin_read_block: %"PRId64" bytes...\n", todo);
+ if (todo < 0 || todo > buf->size) {
+ buf->free_buffer (buf);
+ return NULL;
+ }
+
buf->content = buf->mem;
buf->type = BUF_DEMUX_BLOCK;
@@ -123,10 +129,16 @@ static off_t rtsp_plugin_seek (input_plugin_t *this_gen, off_t offset, int origi
if ((origin == SEEK_CUR) && (offset >= 0)) {
for (;((int)offset) - BUFSIZE > 0; offset -= BUFSIZE) {
- this->curpos += rtsp_plugin_read (this_gen, this->scratch, BUFSIZE);
+ off_t n = rtsp_plugin_read (this_gen, this->scratch, BUFSIZE);
+ if (n <= 0)
+ return this->curpos;
+ this->curpos += n;
}
- this->curpos += rtsp_plugin_read (this_gen, this->scratch, offset);
+ off_t n = rtsp_plugin_read (this_gen, this->scratch, offset);
+ if (n <= 0)
+ return this->curpos;
+ this->curpos += n;
}
return this->curpos;
diff --git a/src/input/input_smb.c b/src/input/input_smb.c
index 3d495f04e..4d7e9a94a 100644
--- a/src/input/input_smb.c
+++ b/src/input/input_smb.c
@@ -69,6 +69,8 @@ smb_plugin_read (input_plugin_t *this_gen, char *buf, off_t len)
smb_input_t *this = (smb_input_t *) this_gen;
off_t n, num_bytes;
+ if (len < 0)
+ return -1;
num_bytes = 0;
while (num_bytes < len)
@@ -89,6 +91,11 @@ smb_plugin_read_block (input_plugin_t *this_gen, fifo_buffer_t *fifo,
off_t total_bytes;
buf_element_t *buf = fifo->buffer_pool_alloc (fifo);
+ if (todo < 0 || todo > buf->size) {
+ buf->free_buffer (buf);
+ return NULL;
+ }
+
buf->content = buf->mem;
buf->type = BUF_DEMUX_BLOCK;
diff --git a/src/input/input_stdin_fifo.c b/src/input/input_stdin_fifo.c
index 0ae841b4b..4acd825a5 100644
--- a/src/input/input_stdin_fifo.c
+++ b/src/input/input_stdin_fifo.c
@@ -85,6 +85,8 @@ static off_t stdin_plugin_read (input_plugin_t *this_gen,
off_t n, total;
lprintf ("reading %"PRId64" bytes...\n", len);
+ if (len < 0)
+ return -1;
total=0;
if (this->curpos < this->preview_size) {
@@ -121,6 +123,11 @@ static buf_element_t *stdin_plugin_read_block (input_plugin_t *this_gen, fifo_bu
/* stdin_input_plugin_t *this = (stdin_input_plugin_t *) this_gen; */
buf_element_t *buf = fifo->buffer_pool_alloc (fifo);
+ if (todo < 0 || todo > buf->size) {
+ buf->free_buffer (buf);
+ return NULL;
+ }
+
buf->content = buf->mem;
buf->type = BUF_DEMUX_BLOCK;
@@ -146,7 +153,7 @@ static off_t stdin_plugin_seek (input_plugin_t *this_gen, off_t offset, int orig
if ((origin == SEEK_CUR) && (offset >= 0)) {
for (;((int)offset) - BUFSIZE > 0; offset -= BUFSIZE) {
- if( !this_gen->read (this_gen, this->seek_buf, BUFSIZE) )
+ if( this_gen->read (this_gen, this->seek_buf, BUFSIZE) <= 0 )
return this->curpos;
}
@@ -168,7 +175,7 @@ static off_t stdin_plugin_seek (input_plugin_t *this_gen, off_t offset, int orig
offset -= this->curpos;
for (;((int)offset) - BUFSIZE > 0; offset -= BUFSIZE) {
- if( !this_gen->read (this_gen, this->seek_buf, BUFSIZE) )
+ if( this_gen->read (this_gen, this->seek_buf, BUFSIZE) <= 0 )
return this->curpos;
}
@@ -270,6 +277,8 @@ static int stdin_plugin_open (input_plugin_t *this_gen ) {
this->preview_size = stdin_plugin_read (&this->input_plugin, this->preview,
MAX_PREVIEW_SIZE);
+ if (this->preview_size < 0)
+ this->preview_size = 0;
this->curpos = 0;
return 1;
diff --git a/src/libsputext/demux_sputext.c b/src/libsputext/demux_sputext.c
index 3e9efb079..198c30498 100644
--- a/src/libsputext/demux_sputext.c
+++ b/src/libsputext/demux_sputext.c
@@ -147,7 +147,7 @@ static inline void trail_space(char *s) {
static char *read_line_from_input(demux_sputext_t *this, char *line, off_t len) {
off_t nread = 0;
- if ((len - this->buflen) > 512) {
+ if ((len - this->buflen) > 512 && len < SUB_BUFSIZE) {
if((nread = this->input->read(this->input,
&this->buf[this->buflen], len - this->buflen)) < 0) {
xprintf(this->stream->xine, XINE_VERBOSITY_DEBUG, "read failed.\n");