[xiph-commits] r14071 - in trunk/speex: include/speex libspeex

jm at svn.xiph.org jm at svn.xiph.org
Tue Oct 30 23:32:55 PDT 2007


Author: jm
Date: 2007-10-30 23:32:54 -0700 (Tue, 30 Oct 2007)
New Revision: 14071

Modified:
   trunk/speex/include/speex/speex_jitter.h
   trunk/speex/libspeex/jitter.c
Log:
jitter buffer: implemented delay steps, tick() no longer required, added
desired_span argument to get()


Modified: trunk/speex/include/speex/speex_jitter.h
===================================================================
--- trunk/speex/include/speex/speex_jitter.h	2007-10-30 21:34:52 UTC (rev 14070)
+++ trunk/speex/include/speex/speex_jitter.h	2007-10-31 06:32:54 UTC (rev 14071)
@@ -82,13 +82,23 @@
 /** Get minimum amount of extra buffering required (margin) */
 #define JITTER_BUFFER_GET_MARGIN 1
 /* JITTER_BUFFER_SET_AVAILABLE_COUNT wouldn't make sense */
+
 /** Get the amount of available packets currently buffered */
 #define JITTER_BUFFER_GET_AVAILABLE_COUNT 3
 /** Included because of an early misspelling (will remove in next release) */
 #define JITTER_BUFFER_GET_AVALIABLE_COUNT 3
 
+/**  */
+#define JITTER_BUFFER_SET_DESTROY_CALLBACK 4
+/**  */
+#define JITTER_BUFFER_GET_DESTROY_CALLBACK 5
 
+/**  */
+#define JITTER_BUFFER_SET_DELAY_STEP 6
+/**  */
+#define JITTER_BUFFER_GET_DELAY_STEP 7
 
+
 #define JITTER_BUFFER_ADJUST_INTERPOLATE -1
 #define JITTER_BUFFER_ADJUST_OK 0
 #define JITTER_BUFFER_ADJUST_DROP 1
@@ -125,7 +135,7 @@
  * @param packet Returned packet
  * @param current_timestamp Timestamp for the returned packet 
 */
-int jitter_buffer_get(JitterBuffer *jitter, JitterBufferPacket *packet, spx_int32_t *start_offset);
+int jitter_buffer_get(JitterBuffer *jitter, JitterBufferPacket *packet, spx_int32_t desired_span, spx_int32_t *start_offset);
 
 /** Get pointer timestamp of jitter buffer
  * 

Modified: trunk/speex/libspeex/jitter.c
===================================================================
--- trunk/speex/libspeex/jitter.c	2007-10-30 21:34:52 UTC (rev 14070)
+++ trunk/speex/libspeex/jitter.c	2007-10-31 06:32:54 UTC (rev 14071)
@@ -32,6 +32,15 @@
 
 */
 
+/* TODO:
+ - Implement JITTER_BUFFER_SET_DESTROY_CALLBACK
+ - Implement JITTER_BUFFER_SET_TIME_ADJUST
+ - Get rid of tick()
+ - Multiple get / get_multiple()
+ - User data?
+ - Use JitterBufferPacket internally
+*/
+
 #ifdef HAVE_CONFIG_H
 #include "config.h"
 #endif
@@ -68,8 +77,10 @@
    spx_uint32_t timestamp[SPEEX_JITTER_MAX_BUFFER_SIZE];                  /**< Timestamp of packet                 */
    int span[SPEEX_JITTER_MAX_BUFFER_SIZE];                                /**< Timestamp of packet                 */
    int len[SPEEX_JITTER_MAX_BUFFER_SIZE];                                 /**< Number of bytes in packet           */
-
-   int tick_size;                                                         /**< Output granularity                  */
+   
+   spx_int32_t sub_clock;                                                 /** Time since last get() call (incremented by tick()) */
+   int resolution;                                                        /**< Time resolution for histogram (timestamp units) */
+   int delay_step;                                                        /**< Size of the steps when adjusting buffering (timestamp units) */
    int reset_state;                                                       /**< True if state was just reset        */
    int buffer_margin;                                                     /**< How many frames we want to keep in the buffer (lower bound) */
    int late_cutoff;                                                       /**< How late must a packet be for it not to be considered at all */
@@ -82,7 +93,7 @@
 };
 
 /** Initialise jitter buffer */
-JitterBuffer *jitter_buffer_init(int tick)
+JitterBuffer *jitter_buffer_init(int resolution)
 {
    JitterBuffer *jitter = (JitterBuffer*)speex_alloc(sizeof(JitterBuffer));
    if (jitter)
@@ -90,7 +101,8 @@
       int i;
       for (i=0;i<SPEEX_JITTER_MAX_BUFFER_SIZE;i++)
          jitter->buf[i]=NULL;
-      jitter->tick_size = tick;
+      jitter->resolution = resolution;
+      jitter->delay_step = resolution;
       jitter->buffer_margin = 1;
       jitter->late_cutoff = 50;
       jitter_buffer_reset(jitter);
@@ -136,6 +148,7 @@
 {
    int i,j;
    spx_int32_t arrival_margin;
+   spx_int32_t arrival_time;
    /*fprintf (stderr, "put packet %d %d\n", timestamp, span);*/
    if (jitter->reset_state)
    {
@@ -195,9 +208,18 @@
    jitter->span[i]=packet->span;
    jitter->len[i]=packet->len;
    
+   if (jitter->sub_clock == -1)
+      arrival_time = jitter->pointer_timestamp;
+   else
+      arrival_time = jitter->current_timestamp + jitter->sub_clock;
+   
+   if (jitter->current_timestamp + jitter->sub_clock > jitter->pointer_timestamp)
+      speex_warning("something's wrong with the time");
+   
    /* Adjust the buffer size depending on network conditions.
       The arrival margin is how much in advance (or late) the packet it */
-   arrival_margin = (((spx_int32_t)packet->timestamp) - ((spx_int32_t)jitter->current_timestamp))/jitter->tick_size - jitter->buffer_margin;
+   /* FIXME: We might be one tick off in considering what's late */
+   arrival_margin = (((spx_int32_t)packet->timestamp) - ((spx_int32_t)arrival_time))/jitter->resolution - jitter->buffer_margin;
    
    if (arrival_margin >= -jitter->late_cutoff)
    {
@@ -243,7 +265,7 @@
 }
 
 /** Get one packet from the jitter buffer */
-int jitter_buffer_get(JitterBuffer *jitter, JitterBufferPacket *packet, spx_int32_t *start_offset)
+int jitter_buffer_get(JitterBuffer *jitter, JitterBufferPacket *packet, spx_int32_t desired_span, spx_int32_t *start_offset)
 {
    int i;
    unsigned int j;
@@ -253,29 +275,23 @@
    float ontime_ratio_long;
    float early_ratio_short;
    float early_ratio_long;
-   int chunk_size;
    int incomplete = 0;
    
+   jitter->sub_clock = -1;
+   jitter->current_timestamp = jitter->pointer_timestamp;
+   
    if (jitter->interp_requested)
    {
       jitter->interp_requested = 0;
       if (start_offset)
          *start_offset = 0;
       packet->timestamp = jitter->pointer_timestamp;
-      packet->span = jitter->tick_size;
-      jitter->pointer_timestamp += jitter->tick_size;
+      packet->span = jitter->delay_step;
+      jitter->pointer_timestamp += jitter->delay_step;
       packet->len = 0;
       return JITTER_BUFFER_MISSING;
    }
-   if (LT32(jitter->current_timestamp+jitter->tick_size, jitter->pointer_timestamp))
-   {
-      jitter->current_timestamp = jitter->pointer_timestamp;
-      speex_warning("did you forget to call jitter_buffer_tick() by any chance?");
-   }
    /*fprintf (stderr, "get packet %d %d\n", jitter->pointer_timestamp, jitter->current_timestamp);*/
-
-   /* FIXME: This should be only what remaining of the current tick */
-   chunk_size = jitter->tick_size;
    
    /* Compiling arrival statistics */
    
@@ -309,7 +325,7 @@
    /* Search the buffer for a packet with the right timestamp and spanning the whole current chunk */
    for (i=0;i<SPEEX_JITTER_MAX_BUFFER_SIZE;i++)
    {
-      if (jitter->buf[i] && jitter->timestamp[i]==jitter->pointer_timestamp && GE32(jitter->timestamp[i]+jitter->span[i],jitter->pointer_timestamp+chunk_size))
+      if (jitter->buf[i] && jitter->timestamp[i]==jitter->pointer_timestamp && GE32(jitter->timestamp[i]+jitter->span[i],jitter->pointer_timestamp+desired_span))
          break;
    }
    
@@ -318,7 +334,7 @@
    {
       for (i=0;i<SPEEX_JITTER_MAX_BUFFER_SIZE;i++)
       {
-         if (jitter->buf[i] && LE32(jitter->timestamp[i], jitter->pointer_timestamp) && GE32(jitter->timestamp[i]+jitter->span[i],jitter->pointer_timestamp+chunk_size))
+         if (jitter->buf[i] && LE32(jitter->timestamp[i], jitter->pointer_timestamp) && GE32(jitter->timestamp[i]+jitter->span[i],jitter->pointer_timestamp+desired_span))
             break;
       }
    }
@@ -343,7 +359,7 @@
       for (i=0;i<SPEEX_JITTER_MAX_BUFFER_SIZE;i++)
       {
          /* check if packet starts within current chunk */
-         if (jitter->buf[i] && LT32(jitter->timestamp[i],jitter->pointer_timestamp+chunk_size) && GE32(jitter->timestamp[i],jitter->pointer_timestamp))
+         if (jitter->buf[i] && LT32(jitter->timestamp[i],jitter->pointer_timestamp+desired_span) && GE32(jitter->timestamp[i],jitter->pointer_timestamp))
          {
             if (!found || LT32(jitter->timestamp[i],best_time) || (jitter->timestamp[i]==best_time && GT32(jitter->span[i],best_span)))
             {
@@ -381,7 +397,7 @@
          *start_offset = (spx_int32_t)jitter->timestamp[i]-(spx_int32_t)jitter->pointer_timestamp;
       packet->timestamp = jitter->timestamp[i];
       packet->span = jitter->span[i];
-      /* Point at the end of the current packet */
+      /* Point to the end of the current packet */
       jitter->pointer_timestamp = jitter->timestamp[i]+jitter->span[i];
       if (incomplete)
          return JITTER_BUFFER_INCOMPLETE;
@@ -391,6 +407,7 @@
    
    
    /* If we haven't found anything worth returning */
+   
    /*fprintf (stderr, "not found\n");*/
    jitter->lost_count++;
    /*fprintf (stderr, "m");*/
@@ -399,8 +416,8 @@
    if (start_offset)
       *start_offset = 0;
    packet->timestamp = jitter->pointer_timestamp;
-   packet->span = jitter->tick_size;
-   jitter->pointer_timestamp += chunk_size;
+   packet->span = desired_span;
+   jitter->pointer_timestamp += desired_span;
    packet->len = 0;
    
    /* Adjusting the buffering bssed on the amount of packets that are early/on time/late */   
@@ -416,8 +433,8 @@
       }
       jitter->shortterm_margin[0] = 0;
       jitter->longterm_margin[0] = 0;            
-      jitter->pointer_timestamp -= jitter->tick_size;
-      jitter->current_timestamp -= jitter->tick_size;
+      jitter->pointer_timestamp -= jitter->delay_step;
+      jitter->current_timestamp -= jitter->delay_step;
       /*fprintf (stderr, "i");*/
       /*fprintf (stderr, "interpolate (getting some slack)\n");*/
    }
@@ -434,7 +451,10 @@
 
 void jitter_buffer_tick(JitterBuffer *jitter)
 {
-   jitter->current_timestamp += jitter->tick_size;
+   if (jitter->sub_clock == -1)
+      jitter->sub_clock = 0;
+   else
+      jitter->sub_clock += jitter->resolution;
 }
 
 /* Let the jitter buffer know it's the right time to adjust the buffering delay to the network conditions */
@@ -448,11 +468,6 @@
    float early_ratio_short;
    float early_ratio_long;
    
-   if (LT32(jitter->current_timestamp+jitter->tick_size, jitter->pointer_timestamp))
-   {
-      jitter->current_timestamp = jitter->pointer_timestamp;
-      speex_warning("did you forget to call jitter_buffer_tick() by any chance?");
-   }
    /*fprintf (stderr, "get packet %d %d\n", jitter->pointer_timestamp, jitter->current_timestamp);*/
 
    /* FIXME: This should be only what remaining of the current tick */
@@ -488,8 +503,8 @@
       }
       jitter->shortterm_margin[0] = 0;
       jitter->longterm_margin[0] = 0;            
-      jitter->pointer_timestamp -= jitter->tick_size;
-      jitter->current_timestamp -= jitter->tick_size;
+      jitter->pointer_timestamp -= jitter->delay_step;
+      jitter->current_timestamp -= jitter->delay_step;
       jitter->interp_requested = 1;
       return JITTER_BUFFER_ADJUST_INTERPOLATE;
    
@@ -507,8 +522,8 @@
       jitter->longterm_margin[MAX_MARGIN-1] = 0;      
       /*fprintf (stderr, "drop frame\n");*/
       /*fprintf (stderr, "d");*/
-      jitter->pointer_timestamp += jitter->tick_size;
-      jitter->current_timestamp += jitter->tick_size;
+      jitter->pointer_timestamp += jitter->delay_step;
+      jitter->current_timestamp += jitter->delay_step;
       return JITTER_BUFFER_ADJUST_DROP;
    }
    
@@ -538,6 +553,12 @@
          }
          *(spx_int32_t*)ptr = count;
          break;
+      case JITTER_BUFFER_SET_DELAY_STEP:
+         jitter->delay_step = *(spx_int32_t*)ptr;
+         break;
+      case JITTER_BUFFER_GET_DELAY_STEP:
+         *(spx_int32_t*)ptr = jitter->delay_step;
+         break;
       default:
          speex_warning_int("Unknown jitter_buffer_ctl request: ", request);
          return -1;



More information about the commits mailing list