2 #include "AudioDevice.h"
10 #define FRAMES_PER_BUFFER 256
11 #define INPUT_CHANNELS 1
13 void AudioDevice_nanoSleep(AudioDevice
*self
)
17 struct timespec extra;
20 nanosleep(&rqtp, &extra);
22 usleep(self
->lockSleepMicroSeconds
);
23 //printf("AudioDevice usleep(%i)\n", self->lockSleepMicroSeconds);
26 AudioDevice
*AudioDevice_new(void)
28 AudioDevice
*self
= calloc(1, sizeof(AudioDevice
));
30 self
->writeBuffer
= UArray_new();
31 self
->nextWriteBuffer
= UArray_new();
33 self
->readBuffer
= UArray_new();
34 self
->nextReadBuffer
= UArray_new();
35 self
->maxReadFrame
= 4096 * 100;
36 self
->lockSleepMicroSeconds
= 10;
39 AudioDevice_init(self
);
43 inline void AudioDevice_lock(AudioDevice
*self
)
45 while (self
->locked
) { AudioDevice_nanoSleep(self
); }
49 inline void AudioDevice_unlock(AudioDevice
*self
)
54 int AudioDevice_isLocked(AudioDevice
*self
)
59 void AudioDevice_free(AudioDevice
*self
)
62 AudioDevice_lock(self
);
65 { printf("AudioDevice_free waiting on lock %i\n", self->locked); }
67 AudioDevice_terminate(self
);
69 UArray_free(self
->writeBuffer
);
70 UArray_free(self
->nextWriteBuffer
);
72 UArray_free(self
->readBuffer
);
73 UArray_free(self
->nextReadBuffer
);
78 void AudioDevice_init(AudioDevice
*self
)
81 /*printf("AudioDevice_init\n");*/
82 self
->err
= Pa_Initialize();
83 AudioDevice_checkForError(self
);
86 int AudioDevice_framesPerBuffer(AudioDevice
*self
)
88 return FRAMES_PER_BUFFER
;
91 void AudioDevice_terminate(AudioDevice
*self
)
96 void AudioDevice_isListening_(AudioDevice
*self
, int v
)
98 self
->isListening
= v
;
101 int AudioDevice_isListening(AudioDevice
*self
)
103 return self
->isListening
;
106 void AudioDevice_openForReadingAndWriting(AudioDevice
*self
)
108 AudioDevice_isListening_(self
, 1);
109 AudioDevice_open(self
);
112 void AudioDevice_open(AudioDevice
*self
)
116 self
->err
= Pa_OpenDefaultStream(
118 self
->isListening
? INPUT_CHANNELS
: 0, /* input channels */
119 2, /* stereo output */
121 44100, /* sample rate */
122 FRAMES_PER_BUFFER
, /* frames per buffer */
123 //0, /* number of buffers, if zero then use default minimum */
124 /*AudioDevice_callbackInputTest, */
125 AudioDevice_callback
,
127 ); /* pass our data through to callback */
128 AudioDevice_checkForError(self
);
129 //printf("opening self->needsData = 1\n");
134 inline int AudioDevice_isOpen(AudioDevice
*self
)
136 return (self
->stream
!= NULL
);
139 void AudioDevice_close(AudioDevice
*self
)
141 if (AudioDevice_isOpen(self
))
143 self
->err
= Pa_CloseStream( self
->stream
);
145 AudioDevice_checkForError(self
);
149 void AudioDevice_checkForError(AudioDevice
*self
)
151 if (self
->err
!= paNoError
)
153 AudioDevice_printError(self
);
157 const char *AudioDevice_error(AudioDevice
*self
)
159 return self
->err
? Pa_GetErrorText(self
->err
) : NULL
;
162 void AudioDevice_printError(AudioDevice
*self
)
164 printf("AudioDevice error: %s\n", AudioDevice_error(self
));
167 void AudioDevice_start(AudioDevice
*self
)
169 if (!AudioDevice_isOpen(self
))
171 AudioDevice_open(self
);
174 if (AudioDevice_isOpen(self
) && !AudioDevice_isActive(self
))
176 self
->err
= Pa_StartStream( self
->stream
);
177 AudioDevice_checkForError(self
);
181 void AudioDevice_stop(AudioDevice
*self
)
183 if (AudioDevice_isOpen(self
) && AudioDevice_isActive(self
))
185 self
->err
= Pa_StopStream( self
->stream
);
186 AudioDevice_checkForError(self
);
190 int AudioDevice_isActive(AudioDevice
*self
)
192 return AudioDevice_isOpen(self
) ? Pa_IsStreamActive( self
->stream
) : 0;
195 int AudioDevice_streamTime(AudioDevice
*self
)
197 return AudioDevice_isOpen(self
) ? Pa_GetStreamTime( self
->stream
) : 0;
200 double AudioDevice_cpuLoad(AudioDevice
*self
)
202 return AudioDevice_isOpen(self
) ? Pa_GetStreamCpuLoad( self
->stream
) : 0;
205 int AudioDevice_callbackTest(
208 unsigned long framesPerBuffer
,
213 float *out
= (float *)outputBuffer
;
215 for (frame
= 0; frame
< framesPerBuffer
; frame
++)
217 double k
= frame
+ outTime
;
218 float a
= sin((k
* 4 * 261.6) / 44100.0);
220 out
[frame
*2+1] = 0.0;
226 int AudioDevice_callbackInputTest(
229 unsigned long framesPerBuffer
,
234 float *in
= (float *)inputBuffer
;
235 float *out
= (float *)outputBuffer
;
237 for (frame
= 0; frame
< framesPerBuffer
; frame
++)
239 out
[frame
*2+0] = in
[frame
];
240 out
[frame
*2+1] = in
[frame
];
246 unsigned long AudioDevice_bytesPerFrame(AudioDevice
*self
)
248 return sizeof(float)*2;
251 unsigned long AudioDevice_framesInWriteBuffer(AudioDevice
*self
)
253 return UArray_size(self
->writeBuffer
)/AudioDevice_bytesPerFrame(self
);
256 int AudioDevice_callback(
259 unsigned long framesPerBuffer
,
263 AudioDevice
*self
= (AudioDevice
*)userData
;
264 self
->writeBufferIsEmpty
= 0;
266 //printf("AudioDevice_callback\n");
270 printf("AudioDevice: auto stop portaudio stream\n");
272 } /* return non zero to stop stream */
274 memset(outputBuffer
, 0, framesPerBuffer
*2*4);
276 AudioDevice_lock(self
);
278 /* --- speaker output ----------------------- */
280 if (UArray_size(self
->writeBuffer
) == 0)
282 AudioDevice_swapWriteBuffers(self
);
285 if (UArray_size(self
->writeBuffer
))
287 float *out
= (float *)outputBuffer
;
288 /*int writeFrames = AudioDevice_framesInWriteBuffer(self);*/
289 float *buf
= (float *)UArray_bytes(self
->writeBuffer
);
294 int outFramesLeft
= framesPerBuffer
- outFrame
;
295 int writeFramesLeft
= AudioDevice_framesInWriteBuffer(self
) - self
->writeFrame
;
296 //printf("outFramesLeft = %i\n", outFramesLeft);
298 if (writeFramesLeft
< outFramesLeft
) /* out > in */
300 memcpy(out
+ (outFrame
*2), buf
+ (self
->writeFrame
*2), writeFramesLeft
*2*4);
302 AudioDevice_swapWriteBuffers(self
);
303 buf
= (float *)UArray_bytes(self
->writeBuffer
);
304 outFrame
+= writeFramesLeft
;
306 if (AudioDevice_framesInWriteBuffer(self
) == 0)
308 //memset(out + (outFrame*2), 0, outFramesLeft*2*4);
309 //printf("AudioDevice warning: empty buffer ---------------------------------------\n");
310 self
->writeBufferIsEmpty
= 1;
316 memcpy(out
+ (outFrame
*2), buf
+ (self
->writeFrame
*2), outFramesLeft
*2*4);
317 self
->writeFrame
+= outFramesLeft
;
324 self
->writeBufferIsEmpty
= 1;
328 /* --- mic input ----------------------- */
330 if (inputBuffer
&& self
->isListening
)
332 unsigned long frame
= framesPerBuffer
;
333 float *input
= inputBuffer
;
336 if (self
->readFrame
> self
->maxReadFrame
)
341 UArray_setSize_(self
->readBuffer
,
342 (self
->readFrame
+ framesPerBuffer
) * sizeof(float) /*bytes */ * 2 /* channels */);
344 buf
= (float *)UArray_bytes(self
->readBuffer
);
346 buf
+= self
->readFrame
* 2;
348 // map mono mic input to stereo output
352 *buf
= *input
; buf
++;
353 *buf
= *input
; buf
++;
357 self
->readFrame
+= framesPerBuffer
;
361 AudioDevice_unlock(self
);
365 int AudioDevice_swapWriteBuffers(AudioDevice
*self
)
367 /* clear the current buffer */
368 UArray_setSize_(self
->writeBuffer
, 0);
369 self
->writeFrame
= 0;
371 /* swap if the next one has data */
372 if (UArray_size(self
->nextWriteBuffer
))
374 void *b
= self
->writeBuffer
;
375 self
->writeBuffer
= self
->nextWriteBuffer
;
376 self
->nextWriteBuffer
= b
;
377 //printf("swapping buffers self->needsData = 1\n");
384 int AudioDevice_swapReadBuffers(AudioDevice
*self
)
388 if (UArray_size(self
->readBuffer
))
390 /* clear the next buffer */
391 UArray_setSize_(self
->nextReadBuffer
, 0);
396 void *b
= self
->readBuffer
;
397 self
->readBuffer
= self
->nextReadBuffer
;
398 self
->nextReadBuffer
= b
;
406 void AudioDevice_clearBuffers(AudioDevice
*self
)
408 AudioDevice_lock(self
);
409 UArray_setSize_(self
->readBuffer
, 0);
410 UArray_setSize_(self
->nextReadBuffer
, 0);
411 AudioDevice_unlock(self
);
414 /* --- called from the outside --- */
416 void AudioDevice_writeData_length_(AudioDevice
*self
, uint8_t *data
, size_t numBytes
)
418 self
->writeBufferIsEmpty
= 0;
419 AudioDevice_lock(self
);
420 UArray_appendBytes_size_(self
->nextWriteBuffer
, data
, numBytes
);
422 //printf("writting self->needsData = 0\n");
423 AudioDevice_unlock(self
);
424 AudioDevice_start(self
);
427 void AudioDevice_write_(AudioDevice
*self
, UArray
*buf
)
429 AudioDevice_writeData_length_(self
, UArray_bytes(buf
), UArray_size(buf
));
432 UArray
*AudioDevice_read(AudioDevice
*self
)
434 AudioDevice_start(self
);
435 AudioDevice_lock(self
);
436 AudioDevice_swapReadBuffers(self
);
437 AudioDevice_unlock(self
);
438 return self
->nextReadBuffer
;