[FFmpeg-cvslog] r22715 - trunk/libavcodec/bitstream.c

Loren Merritt lorenm
Wed May 5 03:06:09 CEST 2010


On Wed, 5 May 2010, Uoti Urpala wrote:
> On Tue, 2010-05-04 at 23:59 +0100, M?ns Rullg?rd wrote:
>> Loren Merritt <lorenm at u.washington.edu> writes:
>>>>> a) malloc.
>>>>
>>>> Would this have any measurable impact on performance?  Is this
>>>> function ever called more than once per frame?
>>>
>>> No measurable difference in overall speed for ffvhuff, which has 3
>>> tables per frame.
>>> START_TIMER says that the malloc is 400 cycles on linux/x86_64, which
>>> should make it 0.01% of overall time, or less for large frames.
>> 
>> That settles it for me.
> 
> You can't completely rule out the performance impact of a repeated
> malloc with any simple test. It can depend on usage patterns. There's
> also the effect on memory fragmentation. Even if the code frees the
> memory without any other allocation in between that may not hold
> globally due to other threads. In some cases cache effects may matter
> (malloc is almost certainly worse for cache than stack).

If you want to eliminate some repeated mallocs, then hows about this.
(Can be applied with or without my previous patch.)
Still no statistically significant speed change on linux/x86_64.

--Loren Merritt
-------------- next part --------------
diff --git a/libavcodec/bitstream.c b/libavcodec/bitstream.c
index 03d70ac..bd845e4 100644
--- a/libavcodec/bitstream.c
+++ b/libavcodec/bitstream.c
@@ -279,8 +279,10 @@ int init_vlc_sparse(VLC *vlc, int nb_bits, int nb_codes,
             abort(); // fatal error, we are called on a partially initialized table
         }
     }else {
-        vlc->table = NULL;
-        vlc->table_allocated = 0;
+        if(!(flags & INIT_VLC_REUSE_MEM)){
+            vlc->table = NULL;
+            vlc->table_allocated = 0;
+        }
         vlc->table_size = 0;
     }
 
@@ -325,5 +327,6 @@ int init_vlc_sparse(VLC *vlc, int nb_bits, int nb_codes,
 void free_vlc(VLC *vlc)
 {
     av_freep(&vlc->table);
+    vlc->table_allocated = 0;
 }
 
diff --git a/libavcodec/get_bits.h b/libavcodec/get_bits.h
index c325778..efdc65b 100644
--- a/libavcodec/get_bits.h
+++ b/libavcodec/get_bits.h
@@ -517,6 +517,8 @@ int init_vlc_sparse(VLC *vlc, int nb_bits, int nb_codes,
              int flags);
 #define INIT_VLC_LE         2
 #define INIT_VLC_USE_NEW_STATIC 4
+#define INIT_VLC_REUSE_MEM 8 /**< VLC need not be freed before a re-init,
+                               * but must be zeroed before the first init. */
 void free_vlc(VLC *vlc);
 
 #define INIT_VLC_STATIC(vlc, bits, a,b,c,d,e,f,g, static_size)\
diff --git a/libavcodec/huffyuv.c b/libavcodec/huffyuv.c
index 3b56bb3..4a9eadd 100644
--- a/libavcodec/huffyuv.c
+++ b/libavcodec/huffyuv.c
@@ -292,8 +292,7 @@ static void generate_joint_tables(HYuvContext *s){
                         i++;
                 }
             }
-            free_vlc(&s->vlc[3+p]);
-            init_vlc_sparse(&s->vlc[3+p], VLC_BITS, i, len, 1, 1, bits, 2, 2, symbols, 2, 2, 0);
+            init_vlc_sparse(&s->vlc[3+p], VLC_BITS, i, len, 1, 1, bits, 2, 2, symbols, 2, 2, INIT_VLC_REUSE_MEM);
         }
     }else{
         uint8_t (*map)[4] = (uint8_t(*)[4])s->pix_bgr_map;
@@ -333,8 +332,7 @@ static void generate_joint_tables(HYuvContext *s){
                 }
             }
         }
-        free_vlc(&s->vlc[3]);
-        init_vlc(&s->vlc[3], VLC_BITS, i, len, 1, 1, bits, 2, 2, 0);
+        init_vlc(&s->vlc[3], VLC_BITS, i, len, 1, 1, bits, 2, 2, INIT_VLC_REUSE_MEM);
     }
 }
 
@@ -355,8 +353,7 @@ for(j=0; j<256; j++){
 printf("%6X, %2d,  %3d\n", s->bits[i][j], s->len[i][j], j);
 }
 #endif
-        free_vlc(&s->vlc[i]);
-        init_vlc(&s->vlc[i], VLC_BITS, 256, s->len[i], 1, 1, s->bits[i], 4, 4, 0);
+        init_vlc(&s->vlc[i], VLC_BITS, 256, s->len[i], 1, 1, s->bits[i], 4, 4, INIT_VLC_REUSE_MEM);
     }
 
     generate_joint_tables(s);
@@ -387,8 +384,7 @@ static int read_old_huffman_tables(HYuvContext *s){
     memcpy(s->len[2] , s->len [1], 256*sizeof(uint8_t));
 
     for(i=0; i<3; i++){
-        free_vlc(&s->vlc[i]);
-        init_vlc(&s->vlc[i], VLC_BITS, 256, s->len[i], 1, 1, s->bits[i], 4, 4, 0);
+        init_vlc(&s->vlc[i], VLC_BITS, 256, s->len[i], 1, 1, s->bits[i], 4, 4, INIT_VLC_REUSE_MEM);
     }
 
     generate_joint_tables(s);
@@ -433,7 +429,7 @@ static av_cold int decode_init(AVCodecContext *avctx)
     HYuvContext *s = avctx->priv_data;
 
     common_init(avctx);
-    memset(s->vlc, 0, 3*sizeof(VLC));
+    memset(s->vlc, 0, sizeof(s->vlc));
 
     avctx->coded_frame= &s->picture;
     s->interlaced= s->height > 288;



More information about the ffmpeg-cvslog mailing list