[Freeswitch-svn] [commit] r5434 - freeswitch/trunk/src/mod/endpoints/mod_portaudio
Freeswitch SVN
anthm at freeswitch.org
Thu Jun 21 18:36:04 EDT 2007
Author: anthm
Date: Thu Jun 21 18:36:04 2007
New Revision: 5434
Modified:
freeswitch/trunk/src/mod/endpoints/mod_portaudio/mod_portaudio.c
freeswitch/trunk/src/mod/endpoints/mod_portaudio/pa_ringbuffer.c
freeswitch/trunk/src/mod/endpoints/mod_portaudio/pa_ringbuffer.h
freeswitch/trunk/src/mod/endpoints/mod_portaudio/pablio.c
freeswitch/trunk/src/mod/endpoints/mod_portaudio/pablio.h
Log:
try to fix latency on portaudio
Modified: freeswitch/trunk/src/mod/endpoints/mod_portaudio/mod_portaudio.c
==============================================================================
--- freeswitch/trunk/src/mod/endpoints/mod_portaudio/mod_portaudio.c (original)
+++ freeswitch/trunk/src/mod/endpoints/mod_portaudio/mod_portaudio.c Thu Jun 21 18:36:04 2007
@@ -29,7 +29,7 @@
* mod_portaudio.c -- PortAudio Endpoint Module
*
*/
-#include <switch.h>
+#include "switch.h"
#include <stdio.h>
#include <stdlib.h>
@@ -47,8 +47,7 @@
static switch_endpoint_interface_t *channel_endpoint_interface;
#define SAMPLE_TYPE paInt16
-//#define SAMPLE_TYPE paFloat32
-typedef short SAMPLE;
+typedef int16_t SAMPLE;
typedef switch_status_t (*pa_command_t) (char **argv, int argc, switch_stream_handle_t *stream);
@@ -268,7 +267,7 @@
if (olen == 0) {
break;
}
- WriteAudioStream(globals.ring_stream, abuf, (long) olen);
+ WriteAudioStream(globals.ring_stream, abuf, (long) olen, globals.read_codec.implementation->microseconds_per_frame / 1000);
}
}
}
@@ -638,7 +637,12 @@
switch_mutex_lock(globals.device_lock);
- if ((samples = ReadAudioStream(globals.audio_stream, globals.read_frame.data, globals.read_codec.implementation->samples_per_frame)) != 0) {
+ if ((samples = ReadAudioStream(globals.audio_stream, globals.read_frame.data,
+ globals.read_codec.implementation->samples_per_frame,
+ globals.read_codec.implementation->microseconds_per_frame / 1000)) == 0) {
+
+ goto cng;
+ } else {
globals.read_frame.datalen = samples * 2;
globals.read_frame.samples = samples;
@@ -682,7 +686,8 @@
if (globals.audio_stream) {
if (switch_test_flag((&globals), GFLAG_EAR)) {
- WriteAudioStream(globals.audio_stream, (short *) frame->data, (int) (frame->datalen / sizeof(SAMPLE)));
+ WriteAudioStream(globals.audio_stream, (short *) frame->data, (int) (frame->datalen / sizeof(SAMPLE)),
+ globals.read_codec.implementation->microseconds_per_frame / 1000);
}
status = SWITCH_STATUS_SUCCESS;
}
Modified: freeswitch/trunk/src/mod/endpoints/mod_portaudio/pa_ringbuffer.c
==============================================================================
--- freeswitch/trunk/src/mod/endpoints/mod_portaudio/pa_ringbuffer.c (original)
+++ freeswitch/trunk/src/mod/endpoints/mod_portaudio/pa_ringbuffer.c Thu Jun 21 18:36:04 2007
@@ -71,27 +71,16 @@
*
****************/
-#if defined(__VIA_HACK__)
-#define NO_BARRIER
-#endif
-
-#if defined(NO_BARRIER)
-# define PaUtil_FullMemoryBarrier()
-# define PaUtil_ReadMemoryBarrier()
-# define PaUtil_WriteMemoryBarrier()
-#else
-
-#if defined(__APPLE__) //|| defined(__FreeBSD__)
+#if defined(HAVE_LIBKERN_OSATOMIC_H) && (defined(__APPLE__) || defined(__FreeBSD__))
# include <libkern/OSAtomic.h>
- /* Here are the memory barrier functions. Mac OS X and FreeBSD only provide
- full memory barriers, so the three types of barriers are the same. */
+ /* Here are the memory barrier functions. Mac OS X and FreeBSD only provide
+ full memory barriers, so the three types of barriers are the same. */
# define PaUtil_FullMemoryBarrier() OSMemoryBarrier()
# define PaUtil_ReadMemoryBarrier() OSMemoryBarrier()
# define PaUtil_WriteMemoryBarrier() OSMemoryBarrier()
#elif defined(__GNUC__)
-
- /* GCC understands volatile asm and "memory" to mean it
- * should not reorder memory read/writes */
+ /* GCC understands volatile __asm__ and "memory" to mean it
+ * should not reorder memory read/writes */
# if defined( __PPC__ )
# define PaUtil_FullMemoryBarrier() __asm__ volatile("sync":::"memory")
# define PaUtil_ReadMemoryBarrier() __asm__ volatile("sync":::"memory")
@@ -101,61 +90,63 @@
# define PaUtil_ReadMemoryBarrier() __asm__ volatile("lfence":::"memory")
# define PaUtil_WriteMemoryBarrier() __asm__ volatile("sfence":::"memory")
# else
+# ifdef ALLOW_SMP_DANGERS
+# warning Memory barriers not defined on this system or system unknown
+# warning For SMP safety, you should fix this.
+# define PaUtil_FullMemoryBarrier()
+# define PaUtil_ReadMemoryBarrier()
+# define PaUtil_WriteMemoryBarrier()
+# else
+# error Memory barriers are not defined on this system. You can still compile by defining ALLOW_SMP_DANGERS, but SMP safety will not be guaranteed.
+# endif
+# endif
+#else
+# ifdef ALLOW_SMP_DANGERS
+# warning Memory barriers not defined on this system or system unknown
+# warning For SMP safety, you should fix this.
# define PaUtil_FullMemoryBarrier()
# define PaUtil_ReadMemoryBarrier()
# define PaUtil_WriteMemoryBarrier()
+# else
+# error Memory barriers are not defined on this system. You can still compile by defining ALLOW_SMP_DANGERS, but SMP safety will not be guaranteed.
# endif
-#elif defined(_MSC_VER)
-# include <intrin.h>
-# pragma intrinsic(_ReadWriteBarrier)
-# pragma intrinsic(_ReadBarrier)
-# pragma intrinsic(_WriteBarrier)
-# define PaUtil_FullMemoryBarrier() _ReadWriteBarrier()
-# define PaUtil_ReadMemoryBarrier() _ReadBarrier()
-# define PaUtil_WriteMemoryBarrier() _WriteBarrier()
-#else
-# define PaUtil_FullMemoryBarrier()
-# define PaUtil_ReadMemoryBarrier()
-# define PaUtil_WriteMemoryBarrier()
-#endif
#endif
+
/***************************************************************************
* Initialize FIFO.
* numBytes must be power of 2, returns -1 if not.
*/
-long PaUtil_InitializeRingBuffer(PaUtilRingBuffer * rbuf, long numBytes, void *dataPtr)
+long PaUtil_InitializeRingBuffer( PaUtilRingBuffer *rbuf, long numBytes, void *dataPtr )
{
- if (((numBytes - 1) & numBytes) != 0)
- return -1; /* Not Power of two. */
- rbuf->bufferSize = numBytes;
- rbuf->buffer = (char *) dataPtr;
- PaUtil_FlushRingBuffer(rbuf);
- rbuf->bigMask = (numBytes * 2) - 1;
- rbuf->smallMask = (numBytes) - 1;
- return 0;
+ if( ((numBytes-1) & numBytes) != 0) return -1; /* Not Power of two. */
+ rbuf->bufferSize = numBytes;
+ rbuf->buffer = (char *)dataPtr;
+ PaUtil_FlushRingBuffer( rbuf );
+ rbuf->bigMask = (numBytes*2)-1;
+ rbuf->smallMask = (numBytes)-1;
+ return 0;
}
/***************************************************************************
** Return number of bytes available for reading. */
-long PaUtil_GetRingBufferReadAvailable(PaUtilRingBuffer * rbuf)
+long PaUtil_GetRingBufferReadAvailable( PaUtilRingBuffer *rbuf )
{
- PaUtil_ReadMemoryBarrier();
- return ((rbuf->writeIndex - rbuf->readIndex) & rbuf->bigMask);
+ PaUtil_ReadMemoryBarrier();
+ return ( (rbuf->writeIndex - rbuf->readIndex) & rbuf->bigMask );
}
-
/***************************************************************************
** Return number of bytes available for writing. */
-long PaUtil_GetRingBufferWriteAvailable(PaUtilRingBuffer * rbuf)
+long PaUtil_GetRingBufferWriteAvailable( PaUtilRingBuffer *rbuf )
{
- /* Since we are calling PaUtil_GetRingBufferReadAvailable, we don't need an aditional MB */
- return (rbuf->bufferSize - PaUtil_GetRingBufferReadAvailable(rbuf));
+ /* Since we are calling PaUtil_GetRingBufferReadAvailable, we don't need an aditional MB */
+ return ( rbuf->bufferSize - PaUtil_GetRingBufferReadAvailable(rbuf));
}
/***************************************************************************
** Clear buffer. Should only be called when buffer is NOT being read. */
-void PaUtil_FlushRingBuffer(PaUtilRingBuffer * rbuf)
+void PaUtil_FlushRingBuffer( PaUtilRingBuffer *rbuf )
{
- rbuf->writeIndex = rbuf->readIndex = 0;
+ rbuf->writeIndex = rbuf->readIndex = 0;
}
/***************************************************************************
@@ -164,38 +155,42 @@
** If non-contiguous, size2 will be the size of second region.
** Returns room available to be written or numBytes, whichever is smaller.
*/
-long PaUtil_GetRingBufferWriteRegions(PaUtilRingBuffer * rbuf, long numBytes, void **dataPtr1, long *sizePtr1, void **dataPtr2, long *sizePtr2)
-{
- long index;
- long available = PaUtil_GetRingBufferWriteAvailable(rbuf);
- if (numBytes > available)
- numBytes = available;
- /* Check to see if write is not contiguous. */
- index = rbuf->writeIndex & rbuf->smallMask;
- if ((index + numBytes) > rbuf->bufferSize) {
- /* Write data in two blocks that wrap the buffer. */
- long firstHalf = rbuf->bufferSize - index;
- *dataPtr1 = &rbuf->buffer[index];
- *sizePtr1 = firstHalf;
- *dataPtr2 = &rbuf->buffer[0];
- *sizePtr2 = numBytes - firstHalf;
- } else {
- *dataPtr1 = &rbuf->buffer[index];
- *sizePtr1 = numBytes;
- *dataPtr2 = NULL;
- *sizePtr2 = 0;
- }
- return numBytes;
+long PaUtil_GetRingBufferWriteRegions( PaUtilRingBuffer *rbuf, long numBytes,
+ void **dataPtr1, long *sizePtr1,
+ void **dataPtr2, long *sizePtr2 )
+{
+ long index;
+ long available = PaUtil_GetRingBufferWriteAvailable( rbuf );
+ if( numBytes > available ) numBytes = available;
+ /* Check to see if write is not contiguous. */
+ index = rbuf->writeIndex & rbuf->smallMask;
+ if( (index + numBytes) > rbuf->bufferSize )
+ {
+ /* Write data in two blocks that wrap the buffer. */
+ long firstHalf = rbuf->bufferSize - index;
+ *dataPtr1 = &rbuf->buffer[index];
+ *sizePtr1 = firstHalf;
+ *dataPtr2 = &rbuf->buffer[0];
+ *sizePtr2 = numBytes - firstHalf;
+ }
+ else
+ {
+ *dataPtr1 = &rbuf->buffer[index];
+ *sizePtr1 = numBytes;
+ *dataPtr2 = NULL;
+ *sizePtr2 = 0;
+ }
+ return numBytes;
}
/***************************************************************************
*/
-long PaUtil_AdvanceRingBufferWriteIndex(PaUtilRingBuffer * rbuf, long numBytes)
+long PaUtil_AdvanceRingBufferWriteIndex( PaUtilRingBuffer *rbuf, long numBytes )
{
- /* we need to ensure that previous writes are seen before we update the write index */
- PaUtil_WriteMemoryBarrier();
- return rbuf->writeIndex = (rbuf->writeIndex + numBytes) & rbuf->bigMask;
+ /* we need to ensure that previous writes are seen before we update the write index */
+ PaUtil_WriteMemoryBarrier();
+ return rbuf->writeIndex = (rbuf->writeIndex + numBytes) & rbuf->bigMask;
}
/***************************************************************************
@@ -204,72 +199,81 @@
** If non-contiguous, size2 will be the size of second region.
** Returns room available to be written or numBytes, whichever is smaller.
*/
-long PaUtil_GetRingBufferReadRegions(PaUtilRingBuffer * rbuf, long numBytes, void **dataPtr1, long *sizePtr1, void **dataPtr2, long *sizePtr2)
-{
- long index;
- long available = PaUtil_GetRingBufferReadAvailable(rbuf);
- if (numBytes > available)
- numBytes = available;
- /* Check to see if read is not contiguous. */
- index = rbuf->readIndex & rbuf->smallMask;
- if ((index + numBytes) > rbuf->bufferSize) {
- /* Write data in two blocks that wrap the buffer. */
- long firstHalf = rbuf->bufferSize - index;
- *dataPtr1 = &rbuf->buffer[index];
- *sizePtr1 = firstHalf;
- *dataPtr2 = &rbuf->buffer[0];
- *sizePtr2 = numBytes - firstHalf;
- } else {
- *dataPtr1 = &rbuf->buffer[index];
- *sizePtr1 = numBytes;
- *dataPtr2 = NULL;
- *sizePtr2 = 0;
- }
- return numBytes;
+long PaUtil_GetRingBufferReadRegions( PaUtilRingBuffer *rbuf, long numBytes,
+ void **dataPtr1, long *sizePtr1,
+ void **dataPtr2, long *sizePtr2 )
+{
+ long index;
+ long available = PaUtil_GetRingBufferReadAvailable( rbuf );
+ if( numBytes > available ) numBytes = available;
+ /* Check to see if read is not contiguous. */
+ index = rbuf->readIndex & rbuf->smallMask;
+ if( (index + numBytes) > rbuf->bufferSize )
+ {
+ /* Write data in two blocks that wrap the buffer. */
+ long firstHalf = rbuf->bufferSize - index;
+ *dataPtr1 = &rbuf->buffer[index];
+ *sizePtr1 = firstHalf;
+ *dataPtr2 = &rbuf->buffer[0];
+ *sizePtr2 = numBytes - firstHalf;
+ }
+ else
+ {
+ *dataPtr1 = &rbuf->buffer[index];
+ *sizePtr1 = numBytes;
+ *dataPtr2 = NULL;
+ *sizePtr2 = 0;
+ }
+ return numBytes;
}
-
/***************************************************************************
*/
-long PaUtil_AdvanceRingBufferReadIndex(PaUtilRingBuffer * rbuf, long numBytes)
+long PaUtil_AdvanceRingBufferReadIndex( PaUtilRingBuffer *rbuf, long numBytes )
{
- /* we need to ensure that previous writes are always seen before updating the index. */
- PaUtil_WriteMemoryBarrier();
- return rbuf->readIndex = (rbuf->readIndex + numBytes) & rbuf->bigMask;
+ /* we need to ensure that previous writes are always seen before updating the index. */
+ PaUtil_WriteMemoryBarrier();
+ return rbuf->readIndex = (rbuf->readIndex + numBytes) & rbuf->bigMask;
}
/***************************************************************************
** Return bytes written. */
-long PaUtil_WriteRingBuffer(PaUtilRingBuffer * rbuf, const void *data, long numBytes)
+long PaUtil_WriteRingBuffer( PaUtilRingBuffer *rbuf, const void *data, long numBytes )
{
- long size1, size2, numWritten;
- void *data1, *data2;
- numWritten = PaUtil_GetRingBufferWriteRegions(rbuf, numBytes, &data1, &size1, &data2, &size2);
- if (size2 > 0) {
-
- memcpy(data1, data, size1);
- data = ((char *) data) + size1;
- memcpy(data2, data, size2);
- } else {
- memcpy(data1, data, size1);
- }
- PaUtil_AdvanceRingBufferWriteIndex(rbuf, numWritten);
- return numWritten;
+ long size1, size2, numWritten;
+ void *data1, *data2;
+ numWritten = PaUtil_GetRingBufferWriteRegions( rbuf, numBytes, &data1, &size1, &data2, &size2 );
+ if( size2 > 0 )
+ {
+
+ memcpy( data1, data, size1 );
+ data = ((char *)data) + size1;
+ memcpy( data2, data, size2 );
+ }
+ else
+ {
+ memcpy( data1, data, size1 );
+ }
+ PaUtil_AdvanceRingBufferWriteIndex( rbuf, numWritten );
+ return numWritten;
}
/***************************************************************************
** Return bytes read. */
-long PaUtil_ReadRingBuffer(PaUtilRingBuffer * rbuf, void *data, long numBytes)
+long PaUtil_ReadRingBuffer( PaUtilRingBuffer *rbuf, void *data, long numBytes )
{
- long size1, size2, numRead;
- void *data1, *data2;
- numRead = PaUtil_GetRingBufferReadRegions(rbuf, numBytes, &data1, &size1, &data2, &size2);
- if (size2 > 0) {
- memcpy(data, data1, size1);
- data = ((char *) data) + size1;
- memcpy(data, data2, size2);
- } else {
- memcpy(data, data1, size1);
- }
- PaUtil_AdvanceRingBufferReadIndex(rbuf, numRead);
- return numRead;
+ long size1, size2, numRead;
+ void *data1, *data2;
+ numRead = PaUtil_GetRingBufferReadRegions( rbuf, numBytes, &data1, &size1, &data2, &size2 );
+ if( size2 > 0 )
+ {
+ memcpy( data, data1, size1 );
+ data = ((char *)data) + size1;
+ memcpy( data, data2, size2 );
+ }
+ else
+ {
+ memcpy( data, data1, size1 );
+ }
+ PaUtil_AdvanceRingBufferReadIndex( rbuf, numRead );
+ return numRead;
}
Modified: freeswitch/trunk/src/mod/endpoints/mod_portaudio/pa_ringbuffer.h
==============================================================================
--- freeswitch/trunk/src/mod/endpoints/mod_portaudio/pa_ringbuffer.h (original)
+++ freeswitch/trunk/src/mod/endpoints/mod_portaudio/pa_ringbuffer.h Thu Jun 21 18:36:04 2007
@@ -51,17 +51,19 @@
*/
#ifdef __cplusplus
-extern "C" {
-#endif /* __cplusplus */
-
- typedef struct PaUtilRingBuffer {
- long bufferSize; /* Number of bytes in FIFO. Power of 2. Set by PaUtil_InitRingBuffer. */
- long writeIndex; /* Index of next writable byte. Set by PaUtil_AdvanceRingBufferWriteIndex. */
- long readIndex; /* Index of next readable byte. Set by PaUtil_AdvanceRingBufferReadIndex. */
- long bigMask; /* Used for wrapping indices with extra bit to distinguish full/empty. */
- long smallMask; /* Used for fitting indices to buffer. */
- char *buffer;
- } PaUtilRingBuffer;
+extern "C"
+{
+#endif /* __cplusplus */
+
+typedef struct PaUtilRingBuffer
+{
+ long bufferSize; /* Number of bytes in FIFO. Power of 2. Set by PaUtil_InitRingBuffer. */
+ long writeIndex; /* Index of next writable byte. Set by PaUtil_AdvanceRingBufferWriteIndex. */
+ long readIndex; /* Index of next readable byte. Set by PaUtil_AdvanceRingBufferReadIndex. */
+ long bigMask; /* Used for wrapping indices with extra bit to distinguish full/empty. */
+ long smallMask; /* Used for fitting indices to buffer. */
+ char *buffer;
+}PaUtilRingBuffer;
/** Initialize Ring Buffer.
@@ -74,13 +76,13 @@
@return -1 if numBytes is not a power of 2, otherwise 0.
*/
- long PaUtil_InitializeRingBuffer(PaUtilRingBuffer * rbuf, long numBytes, void *dataPtr);
+long PaUtil_InitializeRingBuffer( PaUtilRingBuffer *rbuf, long numBytes, void *dataPtr );
/** Clear buffer. Should only be called when buffer is NOT being read.
@param rbuf The ring buffer.
*/
- void PaUtil_FlushRingBuffer(PaUtilRingBuffer * rbuf);
+void PaUtil_FlushRingBuffer( PaUtilRingBuffer *rbuf );
/** Retrieve the number of bytes available in the ring buffer for writing.
@@ -88,7 +90,7 @@
@return The number of bytes available for writing.
*/
- long PaUtil_GetRingBufferWriteAvailable(PaUtilRingBuffer * rbuf);
+long PaUtil_GetRingBufferWriteAvailable( PaUtilRingBuffer *rbuf );
/** Retrieve the number of bytes available in the ring buffer for reading.
@@ -96,7 +98,7 @@
@return The number of bytes available for reading.
*/
- long PaUtil_GetRingBufferReadAvailable(PaUtilRingBuffer * rbuf);
+long PaUtil_GetRingBufferReadAvailable( PaUtilRingBuffer *rbuf );
/** Write data to the ring buffer.
@@ -108,7 +110,7 @@
@return The number of bytes written.
*/
- long PaUtil_WriteRingBuffer(PaUtilRingBuffer * rbuf, const void *data, long numBytes);
+long PaUtil_WriteRingBuffer( PaUtilRingBuffer *rbuf, const void *data, long numBytes );
/** Read data from the ring buffer.
@@ -120,7 +122,7 @@
@return The number of bytes read.
*/
- long PaUtil_ReadRingBuffer(PaUtilRingBuffer * rbuf, void *data, long numBytes);
+long PaUtil_ReadRingBuffer( PaUtilRingBuffer *rbuf, void *data, long numBytes );
/** Get address of region(s) to which we can write data.
@@ -142,7 +144,9 @@
@return The room available to be written or numBytes, whichever is smaller.
*/
- long PaUtil_GetRingBufferWriteRegions(PaUtilRingBuffer * rbuf, long numBytes, void **dataPtr1, long *sizePtr1, void **dataPtr2, long *sizePtr2);
+long PaUtil_GetRingBufferWriteRegions( PaUtilRingBuffer *rbuf, long numBytes,
+ void **dataPtr1, long *sizePtr1,
+ void **dataPtr2, long *sizePtr2 );
/** Advance the write index to the next location to be written.
@@ -152,7 +156,7 @@
@return The new position.
*/
- long PaUtil_AdvanceRingBufferWriteIndex(PaUtilRingBuffer * rbuf, long numBytes);
+long PaUtil_AdvanceRingBufferWriteIndex( PaUtilRingBuffer *rbuf, long numBytes );
/** Get address of region(s) from which we can write data.
@@ -174,7 +178,9 @@
@return The number of bytes available for reading.
*/
- long PaUtil_GetRingBufferReadRegions(PaUtilRingBuffer * rbuf, long numBytes, void **dataPtr1, long *sizePtr1, void **dataPtr2, long *sizePtr2);
+long PaUtil_GetRingBufferReadRegions( PaUtilRingBuffer *rbuf, long numBytes,
+ void **dataPtr1, long *sizePtr1,
+ void **dataPtr2, long *sizePtr2 );
/** Advance the read index to the next location to be read.
@@ -184,9 +190,9 @@
@return The new position.
*/
- long PaUtil_AdvanceRingBufferReadIndex(PaUtilRingBuffer * rbuf, long numBytes);
+long PaUtil_AdvanceRingBufferReadIndex( PaUtilRingBuffer *rbuf, long numBytes );
#ifdef __cplusplus
}
-#endif /* __cplusplus */
-#endif /* PA_RINGBUFFER_H */
+#endif /* __cplusplus */
+#endif /* PA_RINGBUFFER_H */
Modified: freeswitch/trunk/src/mod/endpoints/mod_portaudio/pablio.c
==============================================================================
--- freeswitch/trunk/src/mod/endpoints/mod_portaudio/pablio.c (original)
+++ freeswitch/trunk/src/mod/endpoints/mod_portaudio/pablio.c Thu Jun 21 18:36:04 2007
@@ -49,11 +49,12 @@
#include <string.h>
#include <time.h>
+
/************************************************************************/
/******** Constants *****************************************************/
/************************************************************************/
-#define FRAMES_PER_BUFFER (256)
+#define FRAMES_PER_BUFFER (128)
/************************************************************************/
/******** Prototypes ****************************************************/
@@ -117,17 +118,24 @@
* Write data to ring buffer.
* Will not return until all the data has been written.
*/
-long WriteAudioStream(PABLIO_Stream * aStream, void *data, long numFrames)
+long WriteAudioStream(PABLIO_Stream * aStream, void *data, long numFrames, int timeout)
{
long bytesWritten;
char *p = (char *) data;
long numBytes = aStream->bytesPerFrame * numFrames;
+ int time = 0;
+
while (numBytes > 0) {
bytesWritten = PaUtil_WriteRingBuffer(&aStream->outFIFO, p, numBytes);
numBytes -= bytesWritten;
p += bytesWritten;
- if (numBytes > 0)
- Pa_Sleep(10);
+ if (numBytes > 0) {
+ Pa_Sleep(1);
+ if (++time >= timeout * 2) {
+ PaUtil_FlushRingBuffer(&aStream->outFIFO);
+ return 0;
+ }
+ }
}
return numFrames;
}
@@ -136,19 +144,27 @@
* Read data from ring buffer.
* Will not return until all the data has been read.
*/
-long ReadAudioStream(PABLIO_Stream * aStream, void *data, long numFrames)
+long ReadAudioStream(PABLIO_Stream * aStream, void *data, long numFrames, int timeout)
{
long bytesRead;
char *p = (char *) data;
long numBytes = aStream->bytesPerFrame * numFrames;
-
+ int time = 0;
+
while (numBytes > 0) {
bytesRead = PaUtil_ReadRingBuffer(&aStream->inFIFO, p, numBytes);
numBytes -= bytesRead;
p += bytesRead;
- if (numBytes > 0)
- Pa_Sleep(10);
+ if (numBytes > 0) {
+ Pa_Sleep(1);
+ time++;
+ if (time > timeout * 2) {
+ PaUtil_FlushRingBuffer(&aStream->inFIFO);
+ return 0;
+ }
+ }
}
+ //printf("%d\n", time);
return numFrames;
}
@@ -172,18 +188,20 @@
return bytesFull / aStream->bytesPerFrame;
}
-/************************************************************/
+/***********************************************************
static unsigned long RoundUpToNextPowerOf2(unsigned long n)
{
long numBits = 0;
if (((n - 1) & n) == 0)
- return n; /* Already Power of two. */
+ return n;
while (n > 0) {
n = n >> 1;
numBits++;
}
return (1 << numBits);
}
+*/
+
/************************************************************
* Opens a PortAudio stream with default characteristics.
@@ -194,11 +212,11 @@
const PaStreamParameters * inputParameters, const PaStreamParameters * outputParameters, double sampleRate,
PaStreamFlags streamFlags)
{
- long bytesPerSample;
+ long bytesPerSample = 2;
PaError err;
PABLIO_Stream *aStream;
long numFrames;
- long numBytes;
+ //long numBytes;
int channels = 1;
/* Allocate PABLIO_Stream structure for caller. */
@@ -218,12 +236,8 @@
channels = outputParameters->channelCount;
}
- numFrames = 4 * FRAMES_PER_BUFFER;
- numFrames = RoundUpToNextPowerOf2(numFrames);
-
- bytesPerSample = 2;
- aStream->samplesPerFrame = channels;
- aStream->bytesPerFrame = bytesPerSample * aStream->samplesPerFrame;
+ numFrames = FRAMES_PER_BUFFER;
+ aStream->bytesPerFrame = bytesPerSample;
/* Initialize Ring Buffers */
@@ -240,8 +254,8 @@
}
/* Make Write FIFO appear full initially. */
- numBytes = PaUtil_GetRingBufferWriteAvailable(&aStream->outFIFO);
- PaUtil_AdvanceRingBufferWriteIndex(&aStream->outFIFO, numBytes);
+ //numBytes = PaUtil_GetRingBufferWriteAvailable(&aStream->outFIFO);
+ //PaUtil_AdvanceRingBufferWriteIndex(&aStream->outFIFO, numBytes);
/* Open a PortAudio stream that we will use to communicate with the underlying
Modified: freeswitch/trunk/src/mod/endpoints/mod_portaudio/pablio.h
==============================================================================
--- freeswitch/trunk/src/mod/endpoints/mod_portaudio/pablio.h (original)
+++ freeswitch/trunk/src/mod/endpoints/mod_portaudio/pablio.h Thu Jun 21 18:36:04 2007
@@ -61,7 +61,6 @@
PaUtilRingBuffer outFIFO;
PaStream *stream;
int bytesPerFrame;
- int samplesPerFrame;
} PABLIO_Stream;
/* Values for flags for OpenAudioStream(). */
@@ -75,13 +74,13 @@
* Write data to ring buffer.
* Will not return until all the data has been written.
*/
- long WriteAudioStream(PABLIO_Stream * aStream, void *data, long numFrames);
+ long WriteAudioStream(PABLIO_Stream * aStream, void *data, long numFrames, int timeout);
/************************************************************
* Read data from ring buffer.
* Will not return until all the data has been read.
*/
- long ReadAudioStream(PABLIO_Stream * aStream, void *data, long numFrames);
+ long ReadAudioStream(PABLIO_Stream * aStream, void *data, long numFrames, int timeout);
/************************************************************
* Return the number of frames that could be written to the stream without
More information about the Freeswitch-svn
mailing list