diff options
Diffstat (limited to 'kopete/protocols/jabber/jingle/libjingle/talk/third_party/mediastreamer/msfifo.c')
-rw-r--r-- | kopete/protocols/jabber/jingle/libjingle/talk/third_party/mediastreamer/msfifo.c | 168 |
1 files changed, 168 insertions, 0 deletions
diff --git a/kopete/protocols/jabber/jingle/libjingle/talk/third_party/mediastreamer/msfifo.c b/kopete/protocols/jabber/jingle/libjingle/talk/third_party/mediastreamer/msfifo.c new file mode 100644 index 00000000..7e783c24 --- /dev/null +++ b/kopete/protocols/jabber/jingle/libjingle/talk/third_party/mediastreamer/msfifo.c @@ -0,0 +1,168 @@ +/* + The mediastreamer library aims at providing modular media processing and I/O + for linphone, but also for any telephony application. + Copyright (C) 2001 Simon MORLAT simon.morlat@linphone.org + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with this library; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#include <errno.h> +#include <string.h> +#include "msutils.h" +#include "msfifo.h" + +MSFifo * ms_fifo_new(MSBuffer *buf, gint r_gran, gint w_gran, gint r_offset, gint w_offset) +{ + MSFifo *fifo; + gint saved_offset=MAX(r_gran+r_offset,w_offset); + + g_return_val_if_fail(saved_offset<=(buf->size),NULL); + fifo=g_malloc(sizeof(MSFifo)); + fifo->buffer=buf; + fifo->r_gran=r_gran; + fifo->w_gran=w_gran; + fifo->begin=fifo->wr_ptr=fifo->rd_ptr=buf->buffer+saved_offset; + fifo->readsize=0; + fifo->size=fifo->writesize=buf->size-saved_offset; + fifo->saved_offset= saved_offset; + fifo->r_end=fifo->w_end=buf->buffer+buf->size; + fifo->pre_end=fifo->w_end-saved_offset; + buf->ref_count++; + fifo->prev_data=NULL; + fifo->next_data=NULL; + ms_trace("fifo base=%x, begin=%x, end=%x, saved_offset=%i, size=%i" + ,fifo->buffer->buffer,fifo->begin,fifo->w_end,fifo->saved_offset,fifo->size); + return(fifo); +} + +MSFifo * ms_fifo_new_with_buffer(gint r_gran, gint w_gran, gint r_offset, gint w_offset, + gint min_fifo_size) +{ + MSFifo *fifo; + MSBuffer *buf; + gint saved_offset=MAX(r_gran+r_offset,w_offset); + gint fifo_size; + gint tmp; + if (min_fifo_size==0) min_fifo_size=w_gran; + + /* we must allocate a fifo with a size multiple of min_fifo_size, + with a saved_offset */ + if (min_fifo_size>MS_BUFFER_LARGE) + fifo_size=(min_fifo_size) + saved_offset; + else fifo_size=(6*min_fifo_size) + saved_offset; + buf=ms_buffer_new(fifo_size); + fifo=ms_fifo_new(buf,r_gran,w_gran,r_offset,w_offset); + ms_trace("fifo_size=%i",fifo_size); + return(fifo); +} + +void ms_fifo_destroy( MSFifo *fifo) +{ + g_free(fifo); +} + +void ms_fifo_destroy_with_buffer(MSFifo *fifo) +{ + ms_buffer_destroy(fifo->buffer); + ms_fifo_destroy(fifo); +} + +gint ms_fifo_get_read_ptr(MSFifo *fifo, gint bsize, void **ret_ptr) +{ + gchar *rnext; + + *ret_ptr=NULL; + /* //ms_trace("ms_fifo_get_read_ptr: entering.");*/ + g_return_val_if_fail(bsize<=fifo->r_gran,-EINVAL); + + if (bsize>fifo->readsize) + { + ms_trace("Not enough data: bsize=%i, readsize=%i",bsize,fifo->readsize); + return (-ENODATA); + } + + rnext=fifo->rd_ptr+bsize; + if (rnext<=fifo->r_end){ + + *ret_ptr=fifo->rd_ptr; + fifo->rd_ptr=rnext; + }else{ + int unread=fifo->r_end-fifo->rd_ptr; + *ret_ptr=fifo->begin-unread; + memcpy(fifo->buffer->buffer,fifo->r_end-fifo->saved_offset,fifo->saved_offset); + fifo->rd_ptr=(char*)(*ret_ptr) + bsize; + fifo->r_end=fifo->w_end; /* this is important ! */ + ms_trace("moving read ptr to %x",fifo->rd_ptr); + + } + /* update write size*/ + fifo->writesize+=bsize; + fifo->readsize-=bsize; + return bsize; +} + + +void ms_fifo_update_write_ptr(MSFifo *fifo, gint written){ + gint reserved=fifo->wr_ptr-fifo->prev_wr_ptr; + gint unwritten; + g_return_if_fail(reserved>=0); + unwritten=reserved-written; + g_return_if_fail(unwritten>=0); + /* fix readsize and writesize */ + fifo->readsize-=unwritten; + fifo->writesize+=unwritten; + fifo->wr_ptr+=written; +} + +gint ms_fifo_get_write_ptr(MSFifo *fifo, gint bsize, void **ret_ptr) +{ + gchar *wnext; + + *ret_ptr=NULL; + /* //ms_trace("ms_fifo_get_write_ptr: Entering.");*/ + g_return_val_if_fail(bsize<=fifo->w_gran,-EINVAL); + if (bsize>fifo->writesize) + { + ms_trace("Not enough space: bsize=%i, writesize=%i",bsize,fifo->writesize); + *ret_ptr=NULL; + return(-ENODATA); + } + wnext=fifo->wr_ptr+bsize; + if (wnext<=fifo->w_end){ + *ret_ptr=fifo->wr_ptr; + fifo->wr_ptr=wnext; + }else{ + *ret_ptr=fifo->begin; + fifo->r_end=fifo->wr_ptr; + fifo->wr_ptr=fifo->begin+bsize; + ms_trace("moving write ptr to %x",fifo->wr_ptr); + } + fifo->prev_wr_ptr=*ret_ptr; + /* update readsize*/ + fifo->readsize+=bsize; + fifo->writesize-=bsize; + /* //ms_trace("ms_fifo_get_write_ptr: readsize=%i, writesize=%i",fifo->readsize,fifo->writesize);*/ + return bsize; +} + +gint ms_fifo_get_rw_ptr(MSFifo *f1,void **p1,gint minsize1, + MSFifo *f2,void **p2,gint minsize2) +{ + gint rbsize,wbsize; + + rbsize=MIN(f1->readsize,(f1->pre_end-f1->rd_ptr)); + wbsize=MIN(f2->writesize,(f2->w_end-f2->wr_ptr)); + return 0; +} |