[vlc-commits] stream: fix integer overflow with stream_Block()

Rémi Denis-Courmont git at videolan.org
Mon Aug 31 18:59:50 CEST 2015


vlc | branch: master | Rémi Denis-Courmont <remi at remlab.net> | Mon Aug 31 19:59:22 2015 +0300| [b4b8a826398d53328f6d7d4e2630e52f8a0657a1] | committer: Rémi Denis-Courmont

stream: fix integer overflow with stream_Block()

> http://git.videolan.org/gitweb.cgi/vlc.git/?a=commit;h=b4b8a826398d53328f6d7d4e2630e52f8a0657a1
---

 include/vlc_stream.h |    2 +-
 src/input/stream.c   |   38 ++++++++++++++++++++++----------------
 2 files changed, 23 insertions(+), 17 deletions(-)

diff --git a/include/vlc_stream.h b/include/vlc_stream.h
index 289f311..30fde50 100644
--- a/include/vlc_stream.h
+++ b/include/vlc_stream.h
@@ -114,7 +114,7 @@ VLC_API ssize_t stream_Peek(stream_t *, const uint8_t **, size_t);
 VLC_API int stream_vaControl( stream_t *s, int i_query, va_list args );
 VLC_API void stream_Delete( stream_t *s );
 VLC_API int stream_Control( stream_t *s, int i_query, ... );
-VLC_API block_t * stream_Block( stream_t *s, int i_size );
+VLC_API block_t * stream_Block( stream_t *s, size_t );
 VLC_API char * stream_ReadLine( stream_t * );
 VLC_API input_item_t *stream_ReadDir( stream_t * );
 
diff --git a/src/input/stream.c b/src/input/stream.c
index d0e2bf5..ea0eeb9 100644
--- a/src/input/stream.c
+++ b/src/input/stream.c
@@ -29,6 +29,7 @@
 #include <assert.h>
 #include <stdlib.h>
 #include <string.h>
+#include <limits.h>
 
 #include <vlc_common.h>
 #include <vlc_block.h>
@@ -539,27 +540,32 @@ int stream_Control( stream_t *s, int i_query, ... )
 }
 
 /**
- * Read "i_size" bytes and store them in a block_t.
- * It always read i_size bytes unless you are at the end of the stream
- * where it return what is available.
+ * Read data into a block.
+ *
+ * @param s stream to read data from
+ * @param size number of bytes to read
+ * @return a block of data, or NULL on error
+ @ note The block size may be shorter than requested if the end-of-stream was
+ * reached.
  */
-block_t *stream_Block( stream_t *s, int i_size )
+block_t *stream_Block( stream_t *s, size_t size )
 {
-    if( i_size <= 0 ) return NULL;
+    if( unlikely(size > SSIZE_MAX) )
+        return NULL;
 
-    /* emulate block read */
-    block_t *p_bk = block_Alloc( i_size );
-    if( p_bk )
+    block_t *block = block_Alloc( size );
+    if( unlikely(block == NULL) )
+        return NULL;
+
+    ssize_t val = stream_Read( s, block->p_buffer, size );
+    if( val <= 0 )
     {
-        int i_read = stream_Read( s, p_bk->p_buffer, i_size );
-        if( i_read > 0 )
-        {
-            p_bk->i_buffer = i_read;
-            return p_bk;
-        }
-        block_Release( p_bk );
+        block_Release( block );
+        return NULL;
     }
-    return NULL;
+
+    block->i_buffer = val;
+    return block;
 }
 
 /**



More information about the vlc-commits mailing list