]> git.sesse.net Git - vlc/commitdiff
Convert rate stats to integer and remove useless float support
authorRémi Denis-Courmont <remi@remlab.net>
Tue, 29 Nov 2011 19:20:29 +0000 (21:20 +0200)
committerRémi Denis-Courmont <remi@remlab.net>
Tue, 29 Nov 2011 19:33:06 +0000 (21:33 +0200)
This saves a whole lot of float conversion and simplifies the code.

src/input/decoder.c
src/input/es_out.c
src/input/input.c
src/input/stream.c
src/libvlc.h
src/misc/stats.c

index aba9d723ed9b0955f543437773fd8fcfa3e8683a..fe95bb7aa4b2bc023b1089f49fea2e8fc25c89ec 100644 (file)
@@ -1327,14 +1327,9 @@ static void DecoderDecodeAudio( decoder_t *p_dec, block_t *p_block )
     if( p_input != NULL && (i_decoded > 0 || i_lost > 0 || i_played > 0) )
     {
         vlc_mutex_lock( &p_input->p->counters.counters_lock);
-
-        stats_UpdateInteger( p_input->p->counters.p_lost_abuffers,
-                             i_lost, NULL );
-        stats_UpdateInteger( p_input->p->counters.p_played_abuffers,
-                             i_played, NULL );
-        stats_UpdateInteger( p_input->p->counters.p_decoded_audio,
-                             i_decoded, NULL );
-
+        stats_Update( p_input->p->counters.p_lost_abuffers, i_lost, NULL );
+        stats_Update( p_input->p->counters.p_played_abuffers, i_played, NULL );
+        stats_Update( p_input->p->counters.p_decoded_audio, i_decoded, NULL );
         vlc_mutex_unlock( &p_input->p->counters.counters_lock);
     }
 }
@@ -1556,15 +1551,10 @@ static void DecoderDecodeVideo( decoder_t *p_dec, block_t *p_block )
     if( p_input != NULL && (i_decoded > 0 || i_lost > 0 || i_displayed > 0) )
     {
         vlc_mutex_lock( &p_input->p->counters.counters_lock );
-
-        stats_UpdateInteger( p_input->p->counters.p_decoded_video,
-                             i_decoded, NULL );
-        stats_UpdateInteger( p_input->p->counters.p_lost_pictures,
-                             i_lost , NULL);
-
-        stats_UpdateInteger( p_input->p->counters.p_displayed_pictures,
-                             i_displayed, NULL);
-
+        stats_Update( p_input->p->counters.p_decoded_video, i_decoded, NULL );
+        stats_Update( p_input->p->counters.p_lost_pictures, i_lost , NULL);
+        stats_Update( p_input->p->counters.p_displayed_pictures,
+                      i_displayed, NULL);
         vlc_mutex_unlock( &p_input->p->counters.counters_lock );
     }
 }
@@ -1956,7 +1946,7 @@ static void DecoderProcessSpu( decoder_t *p_dec, block_t *p_block, bool b_flush
         if( p_input != NULL )
         {
             vlc_mutex_lock( &p_input->p->counters.counters_lock );
-            stats_UpdateInteger( p_input->p->counters.p_decoded_sub, 1, NULL );
+            stats_Update( p_input->p->counters.p_decoded_sub, 1, NULL );
             vlc_mutex_unlock( &p_input->p->counters.counters_lock );
         }
 
index 7caff19e7731986292a084ae27968b9732320677..89bff72d7f1a0a07ba626b020ace5616e6a00c8c 100644 (file)
@@ -1920,27 +1920,25 @@ static int EsOutSend( es_out_t *out, es_out_id_t *es, block_t *p_block )
 {
     es_out_sys_t   *p_sys = out->p_sys;
     input_thread_t *p_input = p_sys->p_input;
-    int i_total = 0;
 
     if( libvlc_stats( p_input ) )
     {
+        uint64_t i_total;
+
         vlc_mutex_lock( &p_input->p->counters.counters_lock );
-        stats_UpdateInteger( p_input->p->counters.p_demux_read,
-                             p_block->i_buffer, &i_total );
-        stats_UpdateFloat( p_input->p->counters.p_demux_bitrate,
-                           (float)i_total, NULL );
+        stats_Update( p_input->p->counters.p_demux_read,
+                      p_block->i_buffer, &i_total );
+        stats_Update( p_input->p->counters.p_demux_bitrate, i_total, NULL );
 
         /* Update number of corrupted data packats */
         if( p_block->i_flags & BLOCK_FLAG_CORRUPTED )
         {
-            stats_UpdateInteger( p_input->p->counters.p_demux_corrupted,
-                                 1, NULL );
+            stats_Update( p_input->p->counters.p_demux_corrupted, 1, NULL );
         }
         /* Update number of discontinuities */
         if( p_block->i_flags & BLOCK_FLAG_DISCONTINUITY )
         {
-            stats_UpdateInteger( p_input->p->counters.p_demux_discontinuity,
-                                 1, NULL );
+            stats_Update( p_input->p->counters.p_demux_discontinuity, 1, NULL );
         }
         vlc_mutex_unlock( &p_input->p->counters.counters_lock );
     }
index bfe2e3b244e51b4cbef99d55555312f439ffe62e..7b32541f2e2eb2f075ffe0230b5871cc2ba3cbc2 100644 (file)
@@ -851,24 +851,24 @@ static void InitStatistics( input_thread_t * p_input )
     if( p_input->b_preparsing ) return;
 
     /* Prepare statistics */
-#define INIT_COUNTER( c, type, compute ) p_input->p->counters.p_##c = \
- stats_CounterCreate( VLC_VAR_##type, STATS_##compute);
+#define INIT_COUNTER( c, compute ) p_input->p->counters.p_##c = \
+ stats_CounterCreate( STATS_##compute);
     if( libvlc_stats( p_input ) )
     {
-        INIT_COUNTER( read_bytes, INTEGER, COUNTER );
-        INIT_COUNTER( read_packets, INTEGER, COUNTER );
-        INIT_COUNTER( demux_read, INTEGER, COUNTER );
-        INIT_COUNTER( input_bitrate, FLOAT, DERIVATIVE );
-        INIT_COUNTER( demux_bitrate, FLOAT, DERIVATIVE );
-        INIT_COUNTER( demux_corrupted, INTEGER, COUNTER );
-        INIT_COUNTER( demux_discontinuity, INTEGER, COUNTER );
-        INIT_COUNTER( played_abuffers, INTEGER, COUNTER );
-        INIT_COUNTER( lost_abuffers, INTEGER, COUNTER );
-        INIT_COUNTER( displayed_pictures, INTEGER, COUNTER );
-        INIT_COUNTER( lost_pictures, INTEGER, COUNTER );
-        INIT_COUNTER( decoded_audio, INTEGER, COUNTER );
-        INIT_COUNTER( decoded_video, INTEGER, COUNTER );
-        INIT_COUNTER( decoded_sub, INTEGER, COUNTER );
+        INIT_COUNTER( read_bytes, COUNTER );
+        INIT_COUNTER( read_packets, COUNTER );
+        INIT_COUNTER( demux_read, COUNTER );
+        INIT_COUNTER( input_bitrate, DERIVATIVE );
+        INIT_COUNTER( demux_bitrate, DERIVATIVE );
+        INIT_COUNTER( demux_corrupted, COUNTER );
+        INIT_COUNTER( demux_discontinuity, COUNTER );
+        INIT_COUNTER( played_abuffers, COUNTER );
+        INIT_COUNTER( lost_abuffers, COUNTER );
+        INIT_COUNTER( displayed_pictures, COUNTER );
+        INIT_COUNTER( lost_pictures, COUNTER );
+        INIT_COUNTER( decoded_audio, COUNTER );
+        INIT_COUNTER( decoded_video, COUNTER );
+        INIT_COUNTER( decoded_sub, COUNTER );
         p_input->p->counters.p_sout_send_bitrate = NULL;
         p_input->p->counters.p_sout_sent_packets = NULL;
         p_input->p->counters.p_sout_sent_bytes = NULL;
@@ -896,9 +896,9 @@ static int InitSout( input_thread_t * p_input )
         }
         if( libvlc_stats( p_input ) )
         {
-            INIT_COUNTER( sout_sent_packets, INTEGER, COUNTER );
-            INIT_COUNTER( sout_sent_bytes, INTEGER, COUNTER );
-            INIT_COUNTER( sout_send_bitrate, FLOAT, DERIVATIVE );
+            INIT_COUNTER( sout_sent_packets, COUNTER );
+            INIT_COUNTER( sout_sent_bytes, COUNTER );
+            INIT_COUNTER( sout_send_bitrate, DERIVATIVE );
         }
     }
     else
@@ -3195,7 +3195,7 @@ void input_UpdateStatistic( input_thread_t *p_input,
     vlc_mutex_lock( &p_input->p->counters.counters_lock);
     switch( i_type )
     {
-#define I(c) stats_UpdateInteger( p_input->p->counters.c, i_delta, NULL )
+#define I(c) stats_Update( p_input->p->counters.c, i_delta, NULL )
     case INPUT_STATISTIC_DECODED_VIDEO:
         I(p_decoded_video);
         break;
@@ -3211,10 +3211,10 @@ void input_UpdateStatistic( input_thread_t *p_input,
 #undef I
     case INPUT_STATISTIC_SENT_BYTE:
     {
-        int i_bytes; /* That's pretty stupid to define it as an integer, it will overflow
-                        really fast ... */
-        if( !stats_UpdateInteger( p_input->p->counters.p_sout_sent_bytes, i_delta, &i_bytes ) )
-            stats_UpdateFloat( p_input->p->counters.p_sout_send_bitrate, i_bytes, NULL );
+        uint64_t bytes;
+
+        stats_Update( p_input->p->counters.p_sout_sent_bytes, i_delta, &bytes );
+        stats_Update( p_input->p->counters.p_sout_send_bitrate, bytes, NULL );
         break;
     }
     default:
index 507a221418be8f2ce0d8f6ca36d51c709c0b7e30..7ac3994f4dc4a4bdea3b04774b797c50c8230df6 100644 (file)
@@ -1680,7 +1680,6 @@ static int AReadStream( stream_t *s, void *p_read, unsigned int i_read )
     access_t *p_access = p_sys->p_access;
     input_thread_t *p_input = s->p_input;
     int i_read_orig = i_read;
-    int i_total = 0;
 
     if( !p_sys->i_list )
     {
@@ -1689,12 +1688,12 @@ static int AReadStream( stream_t *s, void *p_read, unsigned int i_read )
             vlc_object_kill( s );
         if( p_input )
         {
+            uint64_t total;
+
             vlc_mutex_lock( &p_input->p->counters.counters_lock );
-            stats_UpdateInteger( p_input->p->counters.p_read_bytes, i_read,
-                             &i_total );
-            stats_UpdateFloat( p_input->p->counters.p_input_bitrate,
-                           (float)i_total, NULL );
-            stats_UpdateInteger( p_input->p->counters.p_read_packets, 1, NULL );
+            stats_Update( p_input->p->counters.p_read_bytes, i_read, &total );
+            stats_Update( p_input->p->counters.p_input_bitrate, total, NULL );
+            stats_Update( p_input->p->counters.p_read_packets, 1, NULL );
             vlc_mutex_unlock( &p_input->p->counters.counters_lock );
         }
         return i_read;
@@ -1729,11 +1728,12 @@ static int AReadStream( stream_t *s, void *p_read, unsigned int i_read )
     /* Update read bytes in input */
     if( p_input )
     {
+        uint64_t total;
+
         vlc_mutex_lock( &p_input->p->counters.counters_lock );
-        stats_UpdateInteger( p_input->p->counters.p_read_bytes, i_read, &i_total );
-        stats_UpdateFloat( p_input->p->counters.p_input_bitrate,
-                       (float)i_total, NULL );
-        stats_UpdateInteger( p_input->p->counters.p_read_packets, 1, NULL );
+        stats_Update( p_input->p->counters.p_read_bytes, i_read, &total );
+        stats_Update( p_input->p->counters.p_input_bitrate, total, NULL );
+        stats_Update( p_input->p->counters.p_read_packets, 1, NULL );
         vlc_mutex_unlock( &p_input->p->counters.counters_lock );
     }
     return i_read;
@@ -1746,7 +1746,6 @@ static block_t *AReadBlock( stream_t *s, bool *pb_eof )
     input_thread_t *p_input = s->p_input;
     block_t *p_block;
     bool b_eof;
-    int i_total = 0;
 
     if( !p_sys->i_list )
     {
@@ -1756,12 +1755,14 @@ static block_t *AReadBlock( stream_t *s, bool *pb_eof )
         if( pb_eof ) *pb_eof = p_access->info.b_eof;
         if( p_input && p_block && libvlc_stats (p_access) )
         {
+            uint64_t total;
+
             vlc_mutex_lock( &p_input->p->counters.counters_lock );
-            stats_UpdateInteger( p_input->p->counters.p_read_bytes,
-                                 p_block->i_buffer, &i_total );
-            stats_UpdateFloat( p_input->p->counters.p_input_bitrate,
-                              (float)i_total, NULL );
-            stats_UpdateInteger( p_input->p->counters.p_read_packets, 1, NULL );
+            stats_Update( p_input->p->counters.p_read_bytes,
+                          p_block->i_buffer, &total );
+            stats_Update( p_input->p->counters.p_input_bitrate,
+                          total, NULL );
+            stats_Update( p_input->p->counters.p_read_packets, 1, NULL );
             vlc_mutex_unlock( &p_input->p->counters.counters_lock );
         }
         return p_block;
@@ -1797,13 +1798,13 @@ static block_t *AReadBlock( stream_t *s, bool *pb_eof )
     {
         if( p_input )
         {
+            uint64_t total;
+
             vlc_mutex_lock( &p_input->p->counters.counters_lock );
-            stats_UpdateInteger( p_input->p->counters.p_read_bytes,
-                                 p_block->i_buffer, &i_total );
-            stats_UpdateFloat( p_input->p->counters.p_input_bitrate,
-                              (float)i_total, NULL );
-            stats_UpdateInteger( p_input->p->counters.p_read_packets,
-                                 1 , NULL);
+            stats_Update( p_input->p->counters.p_read_bytes,
+                          p_block->i_buffer, &total );
+            stats_Update( p_input->p->counters.p_input_bitrate, total, NULL );
+            stats_Update( p_input->p->counters.p_read_packets, 1 , NULL);
             vlc_mutex_unlock( &p_input->p->counters.counters_lock );
         }
     }
index 0c551fea3b61cda1ff3b140627afddb97ab7f982..dcf032d4ead22126f95adad40af45d4b526a536d 100644 (file)
@@ -230,13 +230,12 @@ enum
 
 typedef struct counter_sample_t
 {
-    vlc_value_t value;
-    mtime_t     date;
+    uint64_t value;
+    mtime_t  date;
 } counter_sample_t;
 
 typedef struct counter_t
 {
-    int                 i_type;
     int                 i_compute_type;
     int                 i_samples;
     counter_sample_t ** pp_samples;
@@ -267,58 +266,10 @@ enum
     STATS_LOST_PICTURES,
 };
 
-int stats_Update (counter_t *, vlc_value_t, vlc_value_t *);
-counter_t * stats_CounterCreate (int, int);
-int stats_Get (counter_t *, vlc_value_t*);
-
+counter_t * stats_CounterCreate (int);
+void stats_Update (counter_t *, uint64_t, uint64_t *);
 void stats_CounterClean (counter_t * );
 
-static inline int stats_GetInteger( counter_t *p_counter, int64_t *value )
-{
-    int i_ret;
-    vlc_value_t val; val.i_int = 0;
-    if( !p_counter ) return VLC_EGENERIC;
-    i_ret = stats_Get( p_counter, &val );
-    *value = val.i_int;
-    return i_ret;
-}
-
-static inline int stats_GetFloat( counter_t *p_counter, float *value )
-{
-    int i_ret;
-    vlc_value_t val; val.f_float = 0.0;
-    if( !p_counter ) return VLC_EGENERIC;
-    i_ret = stats_Get( p_counter, &val );
-    *value = val.f_float;
-    return i_ret;
-}
-
-static inline int stats_UpdateInteger( counter_t *p_co, int i, int *pi_new )
-{
-    int i_ret;
-    vlc_value_t val;
-    vlc_value_t new_val; new_val.i_int = 0;
-    if( !p_co ) return VLC_EGENERIC;
-    val.i_int = i;
-    i_ret = stats_Update( p_co, val, &new_val );
-    if( pi_new )
-        *pi_new = new_val.i_int;
-    return i_ret;
-}
-
-static inline int stats_UpdateFloat( counter_t *p_co, float f, float *pf_new )
-{
-    vlc_value_t val;
-    int i_ret;
-    vlc_value_t new_val;new_val.f_float = 0.0;
-    if( !p_co ) return VLC_EGENERIC;
-    val.f_float = f;
-    i_ret =  stats_Update( p_co, val, &new_val );
-    if( pf_new )
-        *pf_new = new_val.f_float;
-    return i_ret;
-}
-
 void stats_ComputeInputStats(input_thread_t*, input_stats_t*);
 void stats_ReinitInputStats(input_stats_t *);
 
index a782668d083de60e32a4a9bddc644703635535bd..ba13f0558cb84b82419a77eecf7acb27f5fc3c26 100644 (file)
  * Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
  *****************************************************************************/
 
-/*****************************************************************************
- * Preamble
- *****************************************************************************/
-
 #ifdef HAVE_CONFIG_H
 # include "config.h"
 #endif
 
 #include <vlc_common.h>
-#include <stdio.h>                                               /* required */
-
 #include "input/input_internal.h"
 
-/*****************************************************************************
- * Local prototypes
- *****************************************************************************/
-static int CounterUpdate( counter_t *p_counter,
-                          vlc_value_t val, vlc_value_t * );
-
-/*****************************************************************************
- * Exported functions
- *****************************************************************************/
-
 /**
  * Create a statistics counter
- * \param i_type the type of stored data. One of VLC_VAR_STRING,
- * VLC_VAR_INTEGER, VLC_VAR_FLOAT
  * \param i_compute_type the aggregation type. One of STATS_LAST (always
  * keep the last value), STATS_COUNTER (increment by the passed value),
  * STATS_MAX (keep the maximum passed value), STATS_MIN, or STATS_DERIVATIVE
  * (keep a time derivative of the value)
  */
-counter_t * stats_CounterCreate( int i_type, int i_compute_type )
+counter_t * stats_CounterCreate( int i_compute_type )
 {
     counter_t *p_counter = (counter_t*) malloc( sizeof( counter_t ) ) ;
 
     if( !p_counter ) return NULL;
     p_counter->i_compute_type = i_compute_type;
-    p_counter->i_type = i_type;
     p_counter->i_samples = 0;
     p_counter->pp_samples = NULL;
 
@@ -68,65 +49,20 @@ counter_t * stats_CounterCreate( int i_type, int i_compute_type )
     return p_counter;
 }
 
-/** Update a counter element with new values
- * \param p_counter the counter to update
- * \param val the vlc_value union containing the new value to aggregate. For
- * more information on how data is aggregated, \see stats_Create
- * \param val_new a pointer that will be filled with new data
- */
-int stats_Update( counter_t *p_counter,
-                  vlc_value_t val, vlc_value_t *val_new )
+static inline int64_t stats_GetTotal(const counter_t *counter)
 {
-    if( !p_counter ) return VLC_EGENERIC;
-    return CounterUpdate( p_counter, val, val_new );
+    if (counter == NULL || counter->i_samples == 0)
+        return 0;
+    return counter->pp_samples[0]->value;
 }
 
-/** Get the aggregated value for a counter
- * \param p_this an object
- * \param p_counter the counter
- * \param val a pointer to an initialized vlc_value union. It will contain the
- * retrieved value
- * \return an error code
- */
-int stats_Get( counter_t *p_counter, vlc_value_t *val )
+static inline float stats_GetRate(const counter_t *counter)
 {
-    if( !p_counter || p_counter->i_samples == 0 )
-    {
-        val->i_int = 0;
-        return VLC_EGENERIC;
-    }
+    if (counter == NULL || counter->i_samples < 2)
+        return 0.;
 
-    switch( p_counter->i_compute_type )
-    {
-    case STATS_COUNTER:
-        *val = p_counter->pp_samples[0]->value;
-        break;
-    case STATS_DERIVATIVE:
-        /* Not ready yet */
-        if( p_counter->i_samples < 2 )
-        {
-            val->i_int = 0;
-            return VLC_EGENERIC;
-        }
-        if( p_counter->i_type == VLC_VAR_INTEGER )
-        {
-            float f = ( p_counter->pp_samples[0]->value.i_int -
-                        p_counter->pp_samples[1]->value.i_int ) /
-                    (float)(  p_counter->pp_samples[0]->date -
-                              p_counter->pp_samples[1]->date );
-            val->i_int = (int64_t)f;
-        }
-        else
-        {
-            float f = (float)( p_counter->pp_samples[0]->value.f_float -
-                               p_counter->pp_samples[1]->value.f_float ) /
-                      (float)( p_counter->pp_samples[0]->date -
-                               p_counter->pp_samples[1]->date );
-            val->f_float = f;
-        }
-        break;
-    }
-    return VLC_SUCCESS;;
+    return (counter->pp_samples[0]->value - counter->pp_samples[1]->value)
+        / (float)(counter->pp_samples[0]->date - counter->pp_samples[1]->date);
 }
 
 input_stats_t *stats_NewInputStats( input_thread_t *p_input )
@@ -142,60 +78,45 @@ input_stats_t *stats_NewInputStats( input_thread_t *p_input )
     return p_stats;
 }
 
-void stats_ComputeInputStats( input_thread_t *p_input, input_stats_t *p_stats )
+void stats_ComputeInputStats(input_thread_t *input, input_stats_t *st)
 {
-    if( !libvlc_stats (p_input) ) return;
+    if (!libvlc_stats(input))
+        return;
 
-    vlc_mutex_lock( &p_input->p->counters.counters_lock );
-    vlc_mutex_lock( &p_stats->lock );
+    vlc_mutex_lock(&input->p->counters.counters_lock);
+    vlc_mutex_lock(&st->lock);
 
     /* Input */
-    stats_GetInteger( p_input->p->counters.p_read_packets,
-                      &p_stats->i_read_packets );
-    stats_GetInteger( p_input->p->counters.p_read_bytes,
-                      &p_stats->i_read_bytes );
-    stats_GetFloat( p_input->p->counters.p_input_bitrate,
-                    &p_stats->f_input_bitrate );
-    stats_GetInteger( p_input->p->counters.p_demux_read,
-                      &p_stats->i_demux_read_bytes );
-    stats_GetFloat( p_input->p->counters.p_demux_bitrate,
-                    &p_stats->f_demux_bitrate );
-    stats_GetInteger( p_input->p->counters.p_demux_corrupted,
-                      &p_stats->i_demux_corrupted );
-    stats_GetInteger( p_input->p->counters.p_demux_discontinuity,
-                      &p_stats->i_demux_discontinuity );
+    st->i_read_packets = stats_GetTotal(input->p->counters.p_read_packets);
+    st->i_read_bytes = stats_GetTotal(input->p->counters.p_read_bytes);
+    st->f_input_bitrate = stats_GetRate(input->p->counters.p_input_bitrate);
+    st->i_demux_read_bytes = stats_GetTotal(input->p->counters.p_demux_read);
+    st->f_demux_bitrate = stats_GetRate(input->p->counters.p_demux_bitrate);
+    st->i_demux_corrupted = stats_GetTotal(input->p->counters.p_demux_corrupted);
+    st->i_demux_discontinuity = stats_GetTotal(input->p->counters.p_demux_discontinuity);
 
     /* Decoders */
-    stats_GetInteger( p_input->p->counters.p_decoded_video,
-                      &p_stats->i_decoded_video );
-    stats_GetInteger( p_input->p->counters.p_decoded_audio,
-                      &p_stats->i_decoded_audio );
+    st->i_decoded_video = stats_GetTotal(input->p->counters.p_decoded_video);
+    st->i_decoded_audio = stats_GetTotal(input->p->counters.p_decoded_audio);
 
     /* Sout */
-    if( p_input->p->counters.p_sout_send_bitrate )
+    if (input->p->counters.p_sout_send_bitrate)
     {
-        stats_GetInteger( p_input->p->counters.p_sout_sent_packets,
-                          &p_stats->i_sent_packets );
-        stats_GetInteger( p_input->p->counters.p_sout_sent_bytes,
-                          &p_stats->i_sent_bytes );
-        stats_GetFloat  ( p_input->p->counters.p_sout_send_bitrate,
-                          &p_stats->f_send_bitrate );
+        st->i_sent_packets = stats_GetTotal(input->p->counters.p_sout_sent_packets);
+        st->i_sent_bytes = stats_GetTotal(input->p->counters.p_sout_sent_bytes);
+        st->f_send_bitrate = stats_GetRate(input->p->counters.p_sout_send_bitrate);
     }
 
     /* Aout */
-    stats_GetInteger( p_input->p->counters.p_played_abuffers,
-                      &p_stats->i_played_abuffers );
-    stats_GetInteger( p_input->p->counters.p_lost_abuffers,
-                      &p_stats->i_lost_abuffers );
+    st->i_played_abuffers = stats_GetTotal(input->p->counters.p_played_abuffers);
+    st->i_lost_abuffers = stats_GetTotal(input->p->counters.p_lost_abuffers);
 
     /* Vouts */
-    stats_GetInteger( p_input->p->counters.p_displayed_pictures,
-                      &p_stats->i_displayed_pictures );
-    stats_GetInteger( p_input->p->counters.p_lost_pictures,
-                      &p_stats->i_lost_pictures );
+    st->i_displayed_pictures = stats_GetTotal(input->p->counters.p_displayed_pictures);
+    st->i_lost_pictures = stats_GetTotal(input->p->counters.p_lost_pictures);
 
-    vlc_mutex_unlock( &p_stats->lock );
-    vlc_mutex_unlock( &p_input->p->counters.counters_lock );
+    vlc_mutex_unlock(&st->lock);
+    vlc_mutex_unlock(&input->p->counters.counters_lock);
 }
 
 void stats_ReinitInputStats( input_stats_t *p_stats )
@@ -231,21 +152,17 @@ void stats_CounterClean( counter_t *p_c )
 }
 
 
-/********************************************************************
- * Following functions are local
- ********************************************************************/
-
-/**
- * Update a statistics counter, according to its type
- * If needed, perform a bit of computation (derivative, mostly)
- * This function must be entered with stats handler lock
+/** Update a counter element with new values
  * \param p_counter the counter to update
- * \param val the "new" value
- * \return an error code
+ * \param val the vlc_value union containing the new value to aggregate. For
+ * more information on how data is aggregated, \see stats_Create
+ * \param val_new a pointer that will be filled with new data
  */
-static int CounterUpdate( counter_t *p_counter,
-                          vlc_value_t val, vlc_value_t *new_val )
+void stats_Update( counter_t *p_counter, uint64_t val, uint64_t *new_val )
 {
+    if( !p_counter )
+        return;
+
     switch( p_counter->i_compute_type )
     {
     case STATS_DERIVATIVE:
@@ -253,9 +170,7 @@ static int CounterUpdate( counter_t *p_counter,
         counter_sample_t *p_new, *p_old;
         mtime_t now = mdate();
         if( now - p_counter->last_update < CLOCK_FREQ )
-        {
-            return VLC_EGENERIC;
-        }
+            return;
         p_counter->last_update = now;
         /* Insert the new one at the beginning */
         p_new = (counter_sample_t*)malloc( sizeof( counter_sample_t ) );
@@ -277,27 +192,17 @@ static int CounterUpdate( counter_t *p_counter,
         {
             counter_sample_t *p_new = (counter_sample_t*)malloc(
                                                sizeof( counter_sample_t ) );
-            p_new->value.i_int = 0;
+            p_new->value = 0;
 
             INSERT_ELEM( p_counter->pp_samples, p_counter->i_samples,
                          p_counter->i_samples, p_new );
         }
         if( p_counter->i_samples == 1 )
         {
-            switch( p_counter->i_type )
-            {
-            case VLC_VAR_INTEGER:
-                p_counter->pp_samples[0]->value.i_int += val.i_int;
-                if( new_val )
-                    new_val->i_int = p_counter->pp_samples[0]->value.i_int;
-                break;
-            case VLC_VAR_FLOAT:
-                p_counter->pp_samples[0]->value.f_float += val.f_float;
-                if( new_val )
-                    new_val->f_float = p_counter->pp_samples[0]->value.f_float;
-            }
+            p_counter->pp_samples[0]->value += val;
+            if( new_val )
+                *new_val = p_counter->pp_samples[0]->value;
         }
         break;
     }
-    return VLC_SUCCESS;
 }