]> git.mxchange.org Git - flightgear.git/blob - 3rdparty/iaxclient/lib/audio_portaudio.c
VS2015 compatability fixes.
[flightgear.git] / 3rdparty / iaxclient / lib / audio_portaudio.c
1 /*
2  * iaxclient: a cross-platform IAX softphone library
3  *
4  * Copyrights:
5  * Copyright (C) 2003-2006, Horizon Wimba, Inc.
6  * Copyright (C) 2007, Wimba, Inc.
7  *
8  * Contributors:
9  * Steve Kann <stevek@stevek.com>
10  * Michael Van Donselaar <mvand@vandonselaar.org>
11  * Shawn Lawrence <shawn.lawrence@terracecomm.com>
12  * Erik Bunce <kde@bunce.us>
13  *
14  * This program is free software, distributed under the terms of
15  * the GNU Lesser (Library) General Public License.
16  *
17  * Module: audio_portaudio
18  * Purpose: Audio code to provide portaudio driver support for IAX library
19  * Developed by: Shawn Lawrence, Terrace Communications Inc.
20  * Creation Date: April 18, 2003
21  *
22  * This library uses the PortAudio Portable Audio Library
23  * For more information see: http://www.portaudio.com/
24  * PortAudio Copyright (c) 1999-2000 Ross Bencina and Phil Burk
25  *
26  */
27
28 #if defined(WIN32)  ||  defined(_WIN32_WCE)
29 #include <stdlib.h>
30 #define strcasecmp _stricmp
31 #else
32 #include <strings.h>
33 #endif
34
35 #include "audio_portaudio.h"
36 #include "iaxclient_lib.h"
37 #include "ringbuffer.h"
38 #include "portmixer.h"
39
40 #ifdef USE_MEC2
41 #define DO_EC
42 #include "mec3.h"
43 static echo_can_state_t *ec;
44 #endif
45
46 #ifdef SPAN_EC
47 #define DO_EC
48 #include "ec/echo.h"
49 static echo_can_state_t *ec;
50 #endif
51
52 #if defined(SPEEX_EC) && ! defined (WIN32)
53 #define DO_EC
54 #define restrict __restrict
55 #include "speex/speex_echo.h"
56 static SpeexEchoState *ec;
57 #endif
58
59 #define EC_RING_SZ  8192 /* must be pow(2) */
60
61
62 typedef short SAMPLE;
63
64 static PaStream *iStream, *oStream, *aStream;
65 static PxMixer *iMixer = NULL, *oMixer = NULL;
66
67 static int selectedInput, selectedOutput, selectedRing;
68
69 static int sample_rate = 8000;
70 static int mixers_initialized;
71
72
73 #define MAX_SAMPLE_RATE       48000
74 #ifndef MS_PER_FRAME
75 # define MS_PER_FRAME         40
76 #endif
77 #define SAMPLES_PER_FRAME     (MS_PER_FRAME * sample_rate / 1000)
78
79 /* static frame buffer allocation */
80 #define MAX_SAMPLES_PER_FRAME (MS_PER_FRAME * MAX_SAMPLE_RATE  / 1000)
81
82 /* echo_tail length, in frames must be pow(2) for mec/span ? */
83 #define ECHO_TAIL 4096
84
85 /* RingBuffer Size; Needs to be Pow(2), 1024 = 512 samples = 64ms */
86 #ifndef OUTRBSZ
87 # define OUTRBSZ 32768
88 #endif
89
90 /* Input ringbuffer size;  this doesn't seem to be as critical, and making it big
91  * causes issues when we're answering calls, etc., and the audio system is running
92  * but not being drained */
93 #ifndef INRBSZ
94 # define INRBSZ  2048
95 #endif
96
97 /* TUNING:  The following constants may help in tuning for situations
98  * where you are getting audio-level under/overruns.
99  *
100  * If you are running iaxclient on a system where you cannot get
101  * low-latency scheduling, you may need to increase these.  This tends
102  * to be an issue on non-MacOSX unix systems, when you are not running
103  * as root, and cannot ask the OS for higher priority.
104  *
105  * RBOUTTARGET:  This a target size of the output ringbuffer, in milliseconds,
106  * where audio for your speakers goes after being decoded and mixed, and
107  * before the audio callback asks for it.  It can get larger than this
108  * (up to OUTRBSZ, above), but when it does, for a bit, we will start
109  * dropping some frames.  For no drops at all, this needs to be set to
110  * contain the number of samples in your largest scheduling gap
111  *
112  * PA_NUMBUFFERS:  This is the number of buffers that the low-level
113  * operating system driver will use, for buffering our output (and also
114  * our input) between the soundcard and portaudio.  This should also be
115  * set to the maximum scheduling delay.  Some drivers, though, will
116  * callback _into_ portaudio with a higher priority, so this doesn't
117  * necessarily need to be as big as RBOUTMAXSZ, although on linux, it
118  * does.  The default is to leave this up to portaudio..
119  */
120
121 /* 80ms if average outRing length is more than this many bytes, start dropping */
122 #ifndef RBOUTTARGET
123 # define RBOUTTARGET (80)
124 #endif
125
126 /* size in bytes of ringbuffer target */
127 #define RBOUTTARGET_BYTES (RBOUTTARGET * (sample_rate / 1000) * sizeof(SAMPLE))
128
129 static char inRingBuf[INRBSZ], outRingBuf[OUTRBSZ];
130 static rb_RingBuffer inRing, outRing;
131
132 static int outRingLenAvg;
133
134 static int oneStream;
135 static int auxStream;
136 static int virtualMonoIn;
137 static int virtualMonoOut;
138 static int virtualMonoRing;
139
140 static int running;
141
142 static struct iaxc_sound *sounds;
143 static int  nextSoundId = 1;
144
145 static MUTEX sound_lock;
146
147 /* forward declarations */
148 static int pa_start (struct iaxc_audio_driver *d );
149 static void handle_paerror(PaError err, char * where);
150 static int pa_input_level_set(struct iaxc_audio_driver *d, float level);
151 static float pa_input_level_get(struct iaxc_audio_driver *d);
152
153 /* scan devices and stash pointers to dev structures.
154  *  But, these structures only remain valid while Pa is initialized,
155  *  which, with pablio, is only while it's running!
156  *  Also, storing these things in two separate arrays loses the actual
157  *  PaDeviceID's associated with devices (since their index in these
158  *  input/output arrays isn't the same as their index in the combined
159  *  array */
160 static int scan_devices(struct iaxc_audio_driver *d)
161 {
162         int nDevices;
163         int i;
164
165         d->nDevices = nDevices = Pa_GetDeviceCount();
166         d->devices = (struct iaxc_audio_device *)
167                 malloc(nDevices * sizeof(struct iaxc_audio_device));
168
169         for ( i=0; i < nDevices; i++ )
170         {
171                 const PaDeviceInfo *pa;
172                 struct iaxc_audio_device *dev;
173
174                 pa=Pa_GetDeviceInfo(i);
175                 dev = &(d->devices[i]);
176
177                 if ( pa ) //frik: under Terminal Services this is NULL
178                 {
179                         dev->name = (char *)pa->name;
180                         dev->devID = i;
181                         dev->capabilities = 0;
182
183                         if ( pa->maxInputChannels > 0 )
184                                 dev->capabilities |= IAXC_AD_INPUT;
185
186                         if ( pa->maxOutputChannels > 0 )
187                         {
188                                 dev->capabilities |= IAXC_AD_OUTPUT;
189                                 dev->capabilities |= IAXC_AD_RING;
190                         }
191
192                         if ( i == Pa_GetDefaultInputDevice() )
193                                 dev->capabilities |= IAXC_AD_INPUT_DEFAULT;
194
195                         if ( i == Pa_GetDefaultOutputDevice() )
196                         {
197                                 dev->capabilities |= IAXC_AD_OUTPUT_DEFAULT;
198                                 dev->capabilities |= IAXC_AD_RING_DEFAULT;
199                         }
200                 }
201                 else //frik: under Terminal Services
202                 {
203                         dev->name = "Not usable device";
204                         dev->devID = i;
205                         dev->capabilities = 0;
206                 }
207         }
208
209         return 0;
210 }
211
212 static void mono2stereo(SAMPLE *out, SAMPLE *in, int nSamples)
213 {
214         int i;
215         //fprintf(stderr, "mono2stereo: %d samples\n", nSamples);
216         for ( i=0; i < nSamples; i++ )
217         {
218                 *(out++) = *in;
219                 *(out++) = *(in++);
220         }
221 }
222
223 static void stereo2mono(SAMPLE *out, SAMPLE *in, int nSamples)
224 {
225         int i;
226         //fprintf(stderr, "stereo2mono: %d samples\n", nSamples);
227         for ( i=0; i < nSamples; i++ )
228         {
229                 *(out) = *(in++);
230                 out++; in++;
231                 //*(out++) += *(in++);
232         }
233 }
234
235 static void mix_slin(short *dst, short *src, int samples, int virtualMono)
236 {
237         int i=0,val=0;
238         for ( i=0; i < samples; i++ )
239         {
240                 if ( virtualMono )
241                         val = ((short *)dst)[2*i] + ((short *)src)[i];
242                 else
243                         val = ((short *)dst)[i] + ((short *)src)[i];
244
245                 if ( val > 0x7fff )
246                 {
247                         val = 0x7fff-1;
248                 } else if (val < -0x7fff)
249                 {
250                         val = -0x7fff+1;
251                 }
252
253                 if ( virtualMono )
254                 {
255                         dst[2*i] = val;
256                         dst[2*i+1] = val;
257                 } else
258                 {
259                         dst[i] = val;
260                 }
261
262         }
263 }
264
265 static int pa_mix_sounds (void *outputBuffer, unsigned long frames, int channel, int virtualMono)
266 {
267         struct iaxc_sound *s;
268         struct iaxc_sound **sp;
269         unsigned long outpos;
270
271         MUTEXLOCK(&sound_lock);
272         /* mix each sound into the outputBuffer */
273         sp = &sounds;
274         while ( sp && *sp )
275         {
276                 s = *sp;
277                 outpos = 0;
278
279                 if ( s->channel == channel )
280                 {
281                         /* loop over the sound until we've played it enough
282                          * times, or we've filled the outputBuffer */
283                         for(;;)
284                         {
285                                 int n;
286
287                                 if ( outpos == frames )
288                                         break;  /* we've filled the buffer */
289                                 if ( s->pos == s->len )
290                                 {
291                                         if ( s->repeat == 0 )
292                                         {
293                                                 // XXX free the sound
294                                                 // structure, and maybe the
295                                                 // buffer!
296                                                 (*sp) = s->next;
297                                                 if(s->malloced)
298                                                         free(s->data);
299                                                 free(s);
300                                                 break;
301                                         }
302                                         s->pos = 0;
303                                         s->repeat--;
304                                 }
305
306                                 /* how many frames do we add in this loop? */
307                                 n = (frames - outpos) < (unsigned long)(s->len - s->pos) ?
308                                         (frames - outpos) :
309                                         (unsigned long)(s->len - s->pos);
310
311                                 /* mix in the frames */
312                                 mix_slin((short *)outputBuffer + outpos,
313                                                 s->data+s->pos, n, virtualMono);
314
315                                 s->pos += n;
316                                 outpos += n;
317                         }
318                 }
319                 if ( *sp ) /* don't advance if we removed this member */
320                         sp = &((*sp)->next);
321         }
322         MUTEXUNLOCK(&sound_lock);
323         return 0;
324 }
325
326 static int pa_play_sound(struct iaxc_sound *inSound, int ring)
327 {
328         struct iaxc_sound *sound;
329
330         sound = (struct iaxc_sound *)malloc(sizeof(struct iaxc_sound));
331         if ( !sound )
332                 return 1;
333
334         *sound = *inSound;
335
336         MUTEXLOCK(&sound_lock);
337         sound->channel = ring;
338         sound->id = nextSoundId++;
339         sound->pos = 0;
340
341         sound->next = sounds;
342         sounds = sound;
343         MUTEXUNLOCK(&sound_lock);
344
345         if ( !running )
346                 pa_start(NULL); /* XXX fixme: start/stop semantics */
347
348         return sound->id;
349 }
350
351 static int pa_stop_sound(int soundID)
352 {
353         struct iaxc_sound **sp;
354         int retval = 1; /* not found */
355
356         MUTEXLOCK(&sound_lock);
357         for ( sp = &sounds; *sp; (*sp) = (*sp)->next )
358         {
359                 struct iaxc_sound *s = *sp;
360                 if ( s->id == soundID )
361                 {
362                         if ( s->malloced )
363                                 free(s->data);
364                         /* remove from list */
365                         (*sp) = s->next;
366                         free(s);
367
368                         retval= 0; /* found */
369                         break;
370                 }
371         }
372         MUTEXUNLOCK(&sound_lock);
373
374         return retval; /* found? */
375 }
376
377 static void iaxc_echo_can(short *inputBuffer, short *outputBuffer, int n)
378 {
379         static rb_RingBuffer ecOutRing;
380         static char outRingBuf[EC_RING_SZ];
381         static long bias = 0;
382         short  delayedBuf[1024];
383         int i;
384
385         /* remove bias -- whether ec is on or not. */
386         for ( i = 0; i < n; i++ )
387         {
388                 bias += ((((long int) inputBuffer[i]) << 15) - bias) >> 14;
389                 inputBuffer[i] -= (short int) (bias >> 15);
390         }
391
392         /* if ec is off, clear ec state -- this way, we start fresh if/when
393          * it's turned back on. */
394         if ( !(iaxc_get_filters() & IAXC_FILTER_ECHO) )
395         {
396 #if defined(DO_EC)
397                 if ( ec )
398                 {
399 #if defined(USE_MEC2) || defined(SPAN_EC)
400                         echo_can_free(ec);
401                         ec = NULL;
402 #elif defined(SPEEX_EC)
403                         speex_echo_state_destroy(ec);
404                         ec = NULL;
405 #endif
406                 }
407 #endif
408
409                 return;
410         }
411
412         /* we want echo cancellation */
413
414 #if defined(DO_EC)
415         if ( !ec )
416         {
417                 rb_InitializeRingBuffer(&ecOutRing, EC_RING_SZ, &outRingBuf);
418 #if defined(USE_MEC2) || defined(SPAN_EC)
419                 ec = echo_can_create(ECHO_TAIL, 0);
420 #elif defined(SPEEX_EC)
421                 ec = speex_echo_state_init(SAMPLES_PER_FRAME, ECHO_TAIL);
422 #endif
423         }
424 #endif
425
426         /* fill ecOutRing */
427         rb_WriteRingBuffer(&ecOutRing, outputBuffer, n * 2);
428
429         // Make sure we have enough buffer.
430         // Currently, just one SAMPLES_PER_FRAME's worth.
431         if ( rb_GetRingBufferReadAvailable(&ecOutRing) < ((n + SAMPLES_PER_FRAME) * 2) )
432                 return;
433
434         rb_ReadRingBuffer(&ecOutRing, delayedBuf, n * 2);
435
436 #if defined(DO_EC) && defined(SPEEX_EC)
437         {
438                 short cancelledBuffer[1024];
439
440                 speex_echo_cancel(ec, inputBuffer, delayedBuf,
441                                 cancelledBuffer, NULL);
442
443                 for ( i = 0; i < n; i++ )
444                         inputBuffer[i] = cancelledBuffer[i];
445         }
446 #endif
447
448 #if defined(USE_MEC2) || defined(SPAN_EC)
449         for ( i = 0; i < n; i++ )
450                 inputBuffer[i] = echo_can_update(ec, delayedBuf[i],
451                                 inputBuffer[i]);
452 #endif
453 }
454
455 static int pa_callback(void *inputBuffer, void *outputBuffer,
456             unsigned long samplesPerFrame,
457             const PaStreamCallbackTimeInfo* outTime,
458             PaStreamCallbackFlags statusFlags,
459             void *userData)
460 {
461         int totBytes = samplesPerFrame * sizeof(SAMPLE);
462
463         short virtualInBuffer[MAX_SAMPLES_PER_FRAME * 2];
464         short virtualOutBuffer[MAX_SAMPLES_PER_FRAME * 2];
465
466 #if 0
467         /* I think this can't happen */
468         if(virtualMono && samplesPerFrame > SAMPLES_PER_FRAME) {
469                 fprintf(stderr, "ERROR: buffer in callback is too big!\n");
470                 exit(1);
471         }
472 #endif
473
474         if ( outputBuffer )
475         {
476                 int bWritten;
477                 /* output underflow might happen here */
478                 if (virtualMonoOut)
479                 {
480                         bWritten = rb_ReadRingBuffer(&outRing, virtualOutBuffer,
481                                         totBytes);
482                         /* we zero "virtualOutBuffer", then convert the whole thing,
483                          * yes, because we use virtualOutBuffer for ec below */
484                         if ( bWritten < totBytes )
485                         {
486                                 memset(((char *)virtualOutBuffer) + bWritten,
487                                                 0, totBytes - bWritten);
488                                 //fprintf(stderr, "*U*");
489                         }
490                         mono2stereo((SAMPLE *)outputBuffer, virtualOutBuffer,
491                                         samplesPerFrame);
492                 }
493                 else
494                 {
495                         bWritten = rb_ReadRingBuffer(&outRing, outputBuffer, totBytes);
496                         if ( bWritten < totBytes)
497                         {
498                                 memset((char *)outputBuffer + bWritten,
499                                                 0, totBytes - bWritten);
500                                 //fprintf(stderr, "*U*");
501                         }
502                 }
503
504                 /* zero underflowed space [ silence might be more golden
505                  * than garbage? ] */
506
507                 pa_mix_sounds(outputBuffer, samplesPerFrame, 0, virtualMonoOut);
508
509                 if(!auxStream)
510                         pa_mix_sounds(outputBuffer, samplesPerFrame, 1, virtualMonoOut);
511         }
512
513
514         if ( inputBuffer )
515         {
516                 /* input overflow might happen here */
517                 if ( virtualMonoIn )
518                 {
519                         stereo2mono(virtualInBuffer, (SAMPLE *)inputBuffer,
520                                         samplesPerFrame);
521                         iaxc_echo_can(virtualInBuffer, virtualOutBuffer,
522                                         samplesPerFrame);
523
524                         rb_WriteRingBuffer(&inRing, virtualInBuffer, totBytes);
525                 }
526                 else
527                 {
528                         iaxc_echo_can((short *)inputBuffer,
529                                         (short *)outputBuffer,
530                                         samplesPerFrame);
531
532                         rb_WriteRingBuffer(&inRing, inputBuffer, totBytes);
533                 }
534         }
535
536         return 0;
537 }
538
539 static int pa_aux_callback(void *inputBuffer, void *outputBuffer,
540             unsigned long samplesPerFrame,
541             const PaStreamCallbackTimeInfo* outTime,
542             PaStreamCallbackFlags statusFlags,
543             void *userData)
544 {
545         int totBytes = samplesPerFrame * sizeof(SAMPLE) * (virtualMonoRing + 1);
546
547         if ( outputBuffer )
548         {
549                 memset((char *)outputBuffer, 0, totBytes);
550                 pa_mix_sounds(outputBuffer, samplesPerFrame, 1, virtualMonoRing);
551         }
552         return 0;
553 }
554
555 static int pa_open(int single, int inMono, int outMono)
556 {
557         PaError err;
558         PaDeviceInfo *result;
559
560         struct PaStreamParameters in_stream_params, out_stream_params, no_device;
561         in_stream_params.device = selectedInput;
562         in_stream_params.channelCount = (inMono ? 1 : 2);
563         in_stream_params.sampleFormat = paInt16;
564         result = (PaDeviceInfo *)Pa_GetDeviceInfo(selectedInput);
565         if ( result == NULL ) return -1;
566         in_stream_params.suggestedLatency = result->defaultLowInputLatency;
567         in_stream_params.hostApiSpecificStreamInfo = NULL;
568
569         out_stream_params.device = selectedOutput;
570         out_stream_params.channelCount = (outMono ? 1 : 2);
571         out_stream_params.sampleFormat = paInt16;
572         result = (PaDeviceInfo *)Pa_GetDeviceInfo(selectedOutput);
573         if ( result == NULL ) return -1;
574         out_stream_params.suggestedLatency = result->defaultLowOutputLatency;
575         out_stream_params.hostApiSpecificStreamInfo = NULL;
576
577         no_device.device = paNoDevice;
578         no_device.channelCount = 0;
579         no_device.sampleFormat = paInt16;
580         result = (PaDeviceInfo *)Pa_GetDeviceInfo(selectedInput);
581         if ( result == NULL ) return -1;
582         no_device.suggestedLatency = result->defaultLowInputLatency; // FEEDBACK - unsure if appropriate
583         no_device.hostApiSpecificStreamInfo = NULL;
584
585         if ( single )
586         {
587                 err = Pa_OpenStream(&iStream,
588                         &in_stream_params,
589                         &out_stream_params,
590                         sample_rate,
591                         paFramesPerBufferUnspecified, //FEEBACK - unsure if appropriate
592                         paNoFlag,
593                         (PaStreamCallback *)pa_callback,
594                         NULL);
595                 if (err != paNoError) return -1;
596                 oStream = iStream;
597                 oneStream = 1;
598         } else
599         {
600                 err = Pa_OpenStream(&iStream,
601                         &in_stream_params,
602                         &no_device,
603                         sample_rate,
604                         paFramesPerBufferUnspecified, //FEEBACK - unsure if appropriate
605                         paNoFlag,
606                         (PaStreamCallback *)pa_callback,
607                         NULL);
608                 if ( err != paNoError ) return -1;
609
610                 err = Pa_OpenStream(&oStream,
611                         &no_device,
612                         &out_stream_params,
613                         sample_rate,
614                         paFramesPerBufferUnspecified, //FEEBACK - unsure if appropriate
615                         paNoFlag,
616                         (PaStreamCallback *)pa_callback,
617                         NULL);
618
619                 if ( err != paNoError )
620                 {
621                         Pa_CloseStream(iStream);
622                         iStream = NULL;
623                         return -1;
624                 }
625                 oneStream = 0;
626         }
627
628         virtualMonoIn = (inMono ? 0 : 1);
629         virtualMonoOut = (outMono ? 0 : 1);
630         return 0;
631 }
632
633 /* some commentary here:
634  * 1: MacOSX: MacOSX often needs "virtual mono" and a single stream.
635  * That doesn't work for some USB devices (a Platronics headset), so
636  * mono in, virtual mono out, and mono in/out are also tried.
637  *
638  * 2: Unix/OSS: most cards are OK with real mono, and a single stream.
639  * Except some.  For those, a single open with real mono will succeed,
640  * but execution will fail.  Maybe others will open OK with a single
641  * stream, and real mono, but fail later? Two stream mono is tried first,
642  * since it reportedly provides better sound quality with ALSA
643  * and Sound Blaster Live.
644  *
645  * The failure mode I saw with a volunteer was that reads/writes would
646  * return -enodev (down in the portaudio code).  Bummer.
647  *
648  * Win32 works fine, in all cases, with a single stream and real mono,
649  * so far.
650  *
651  * We could probably do this more cleanly, because there are still cases
652  * where we will fail (i.e. if the user has only mono in and out on a Mac).
653  *
654  * */
655 static int pa_openstreams (struct iaxc_audio_driver *d )
656 {
657         int err;
658
659 #ifdef LINUX
660         err = pa_open(0, 1, 1) && /* two stream mono */
661                 pa_open(1, 1, 1) &&   /* one stream mono */
662                 pa_open(0, 0, 0);     /* two stream stereo */
663 #else
664 #ifdef MACOSX
665         err = pa_open(1, 0, 0) &&  /* one stream stereo */
666                 pa_open(1, 1, 0) &&    /* one stream mono in stereo out */
667                 pa_open(1, 1, 1) &&    /* one stream mono */
668                 pa_open(0, 0, 0);      /* two stream stereo */
669 #else
670         err = pa_open(1, 1, 1) &&  /* one stream mono */
671                 pa_open(1, 0, 0) &&    /* one stream stereo */
672                 pa_open(1, 1, 0) &&    /* one stream mono in stereo out */
673                 pa_open(0, 0, 0);      /* two stream stereo */
674 #endif /*MACOSX */
675 #endif /* LINUX */
676
677         if (err)
678         {
679                 handle_paerror(err, "Unable to open streams");
680                 return -1;
681         }
682         return 0;
683 }
684
685 static int pa_openauxstream (struct iaxc_audio_driver *d )
686 {
687         PaError err;
688
689         struct PaStreamParameters ring_stream_params;
690
691         // setup the ring parameters
692         ring_stream_params.device = selectedRing;
693         ring_stream_params.sampleFormat = paInt16;
694         ring_stream_params.suggestedLatency =
695                 Pa_GetDeviceInfo(selectedRing)->defaultLowOutputLatency;
696         ring_stream_params.hostApiSpecificStreamInfo = NULL;
697
698         // first we'll try mono
699         ring_stream_params.channelCount = 1; 
700
701         err = Pa_OpenStream(&aStream,
702                         NULL,
703                         &ring_stream_params,
704                         sample_rate,
705                         paFramesPerBufferUnspecified, //FEEBACK - unsure if appropriate
706                         paNoFlag,
707                         (PaStreamCallback *)pa_aux_callback,
708                         NULL);
709
710         if ( err != paNoError )
711         {
712                 // next we'll try virtual mono (stereo)
713                 ring_stream_params.channelCount = 1; 
714
715                 err = Pa_OpenStream(&aStream,
716                                 NULL,
717                                 &ring_stream_params,
718                                 sample_rate,
719                                 paFramesPerBufferUnspecified, //FEEBACK - unsure if appropriate
720                                 paNoFlag,
721                                 (PaStreamCallback *)pa_aux_callback,
722                                 NULL);
723         }
724
725         // mmok, failure...
726         if ( err != paNoError )
727         {
728                 // fprintf(stderr, "Failure opening ring device with params: id: %d, output %d, default output %d\n",
729                 // selectedRing, selectedOutput, Pa_GetDefaultOutputDevice());
730
731                 handle_paerror(err, "opening separate ring stream");
732                 return -1;
733         }
734
735         // Determine whether virtual mono is being used
736         virtualMonoRing = ring_stream_params.channelCount - 1;
737
738         return 0;
739 }
740
741 static int pa_start(struct iaxc_audio_driver *d)
742 {
743         static int errcnt = 0;
744
745         if ( running )
746                 return 0;
747
748         /* re-open mixers if necessary */
749         if ( iMixer )
750         {
751                 Px_CloseMixer(iMixer);
752                 iMixer = NULL;
753         }
754
755         if ( oMixer )
756         {
757                 Px_CloseMixer(oMixer);
758                 oMixer = NULL;
759         }
760
761         if ( errcnt > 5 )
762         {
763                 iaxci_usermsg(IAXC_TEXT_TYPE_FATALERROR,
764                                 "iaxclient audio: Can't open Audio Device. "
765                                 "Perhaps you do not have an input or output device?");
766                 /* OK, we'll give the application the option to abort or
767                  * not here, but we will throw a fatal error anyway */
768                 iaxc_millisleep(1000);
769                 //return -1; // Give Up.  Too many errors.
770         }
771
772         /* flush the ringbuffers */
773         rb_InitializeRingBuffer(&inRing, INRBSZ, inRingBuf);
774         rb_InitializeRingBuffer(&outRing, OUTRBSZ, outRingBuf);
775
776         if ( pa_openstreams(d) )
777         {
778                 errcnt++;
779                 return -1;
780         }
781
782         errcnt = 0; // only count consecutive errors.
783
784         if ( Pa_StartStream(iStream) != paNoError )
785                 return -1;
786
787         iMixer = Px_OpenMixer(iStream, 0);
788
789         if ( !oneStream )
790         {
791                 PaError err = Pa_StartStream(oStream);
792                 oMixer = Px_OpenMixer(oStream, 0);
793                 if ( err != paNoError )
794                 {
795                         Pa_StopStream(iStream);
796                         return -1;
797                 }
798         }
799
800         if ( selectedRing != selectedOutput )
801         {
802                 auxStream = 1;
803         }
804         else
805         {
806                 auxStream = 0;
807         }
808
809         if ( auxStream )
810         {
811                 pa_openauxstream(d);
812                 if ( Pa_StartStream(aStream) != paNoError )
813                 {
814                         auxStream = 0;
815                 }
816         }
817
818         /* select the microphone as the input source */
819         if ( iMixer != NULL && !mixers_initialized )
820         {
821                 /* First, select the "microphone" device, if it's available */
822                 /* try the new method, reverting to the old if it fails */
823                 if ( Px_SetCurrentInputSourceByName( iMixer, "microphone" ) != 0 )
824                 {
825                         int n = Px_GetNumInputSources( iMixer ) - 1;
826                         for ( ; n > 0; --n )
827                         {
828                                 if ( !strcasecmp("microphone",
829                                                 Px_GetInputSourceName(iMixer, n)) )
830                                 {
831                                         Px_SetCurrentInputSource( iMixer, n );
832                                 }
833                         }
834                 }
835
836                 /* try to set the microphone boost -- we just turn off this
837                  * "boost" feature, because it often leads to clipping, which
838                  * we can't fix later -- but we can deal with low input levels
839                  * much more gracefully */
840                 Px_SetMicrophoneBoost( iMixer, 0 );
841
842                 /* If the input level is very low, raise it up a bit.
843                  * Otherwise, AGC cannot detect speech, and cannot adjust
844                  * levels */
845                 if ( pa_input_level_get(d) < 0.5f )
846                         pa_input_level_set(d, 0.6f);
847                 mixers_initialized = 1;
848         }
849
850         running = 1;
851         return 0;
852 }
853
854 static int pa_stop (struct iaxc_audio_driver *d )
855 {
856         PaError err;
857
858         if ( !running )
859                 return 0;
860
861         if ( sounds )
862                 return 0;
863
864         err = Pa_AbortStream(iStream);
865         err = Pa_CloseStream(iStream);
866
867         if ( !oneStream )
868         {
869                 err = Pa_AbortStream(oStream);
870                 err = Pa_CloseStream(oStream);
871         }
872
873         if ( auxStream )
874         {
875                 err = Pa_AbortStream(aStream);
876                 err = Pa_CloseStream(aStream);
877         }
878
879         running = 0;
880         return 0;
881 }
882
883 /* Mihai: apparently nobody loves this function. Some actually hate it.
884  * I bet if it's gone, no one will miss it.  Such a cold, cold world!
885 static void pa_shutdown()
886 {
887         CloseAudioStream( iStream );
888         if(!oneStream) CloseAudioStream( oStream );
889         if(auxStream) CloseAudioStream( aStream );
890 }
891 */
892
893 static void handle_paerror(PaError err, char * where)
894 {
895         fprintf(stderr, "PortAudio error at %s: %s\n", where,
896                         Pa_GetErrorText(err));
897 }
898
899 static int pa_input(struct iaxc_audio_driver *d, void *samples, int *nSamples)
900 {
901         int bytestoread;
902
903         bytestoread = *nSamples * sizeof(SAMPLE);
904
905         /* we don't return partial buffers */
906         if ( rb_GetRingBufferReadAvailable(&inRing) < bytestoread )
907         {
908                 *nSamples = 0;
909                 return 0;
910         }
911
912         rb_ReadRingBuffer(&inRing, samples, bytestoread);
913
914         return 0;
915 }
916
917 static int pa_output(struct iaxc_audio_driver *d, void *samples, int nSamples)
918 {
919         int bytestowrite = nSamples * sizeof(SAMPLE);
920         int outRingLen;
921
922         outRingLen = rb_GetRingBufferReadAvailable(&outRing);
923         outRingLenAvg = (outRingLenAvg * 9 + outRingLen ) / 10;
924
925         /* if we've got a big output buffer, drop this */
926         if (outRingLen > (int)RBOUTTARGET_BYTES &&
927                         outRingLenAvg > (int)RBOUTTARGET_BYTES)
928         {
929           //fprintf(stderr, "*O*");
930           return outRingLen/2;
931         }
932
933         //if(rb_GetRingBufferWriteAvailable(&outRing) < bytestowrite)
934         //      fprintf(stderr, "O");
935
936         rb_WriteRingBuffer(&outRing, samples, bytestowrite);
937
938         return (outRingLen + bytestowrite)/2;
939
940 }
941
942 static int pa_select_devices(struct iaxc_audio_driver *d, int input,
943                 int output, int ring)
944 {
945         selectedInput = input;
946         selectedOutput = output;
947         selectedRing = ring;
948         if ( running )
949         {
950                 /* stop/start audio, in order to switch devices */
951                 pa_stop(d);
952                 pa_start(d);
953         }
954         else
955         {
956                 /* start/stop audio, in order to initialize mixers and levels */
957                 pa_start(d);
958                 pa_stop(d);
959         }
960         return 0;
961 }
962
963 static int pa_selected_devices(struct iaxc_audio_driver *d, int *input,
964                 int *output, int *ring)
965 {
966         *input = selectedInput;
967         *output = selectedOutput;
968         *ring = selectedRing;
969         return 0;
970 }
971
972 static int pa_destroy(struct iaxc_audio_driver *d)
973 {
974         if( iMixer )
975         {
976                 Px_CloseMixer(iMixer);
977                 iMixer = NULL;
978         }
979         if ( oMixer )
980         {
981                 Px_CloseMixer(oMixer);
982                 oMixer = NULL;
983         }
984         if ( d )
985         {
986                 if ( d->devices )
987                 {
988                         free(d->devices);
989                         d->devices= NULL;
990                 }
991         }
992         return Pa_Terminate();
993 }
994
995 static float pa_input_level_get(struct iaxc_audio_driver *d)
996 {
997         /* iMixer should be non-null if we using either one or two streams */
998         if ( !iMixer )
999                 return -1;
1000
1001         /* make sure this device supports input volume controls */
1002         if ( Px_GetNumInputSources( iMixer ) == 0 )
1003                 return -1;
1004
1005         return Px_GetInputVolume(iMixer);
1006 }
1007
1008 static float pa_output_level_get(struct iaxc_audio_driver *d)
1009 {
1010         PxMixer *mix;
1011
1012         /* oMixer may be null if we're using one stream,
1013            in which case, iMixer should not be null,
1014            if it is, return an error */
1015
1016         if ( oMixer )
1017                 mix = oMixer;
1018         else if ( iMixer )
1019                 mix = iMixer;
1020         else
1021                 return -1;
1022
1023         /* prefer the pcm output, but default to the master output */
1024         if ( Px_SupportsPCMOutputVolume(mix) )
1025                 return Px_GetPCMOutputVolume(mix);
1026         else
1027                 return Px_GetMasterVolume(mix);
1028 }
1029
1030 static int pa_input_level_set(struct iaxc_audio_driver *d, float level)
1031 {
1032         /* make sure this device supports input volume controls */
1033         if ( !iMixer || Px_GetNumInputSources(iMixer) == 0 )
1034                 return -1;
1035
1036         Px_SetInputVolume(iMixer, level);
1037
1038         return 0;
1039 }
1040
1041 static int pa_output_level_set(struct iaxc_audio_driver *d, float level)
1042 {
1043         PxMixer *mix;
1044
1045         if ( oMixer )
1046                 mix = oMixer;
1047         else if ( iMixer )
1048                 mix = iMixer;
1049         else
1050                 return -1;
1051
1052         /* prefer the pcm output, but default to the master output */
1053         if ( Px_SupportsPCMOutputVolume(mix) )
1054                 Px_SetPCMOutputVolume(mix, level);
1055         else
1056                 Px_SetMasterVolume(mix, level);
1057
1058         return 0;
1059 }
1060
1061 static int pa_mic_boost_get(struct iaxc_audio_driver* d)
1062 {
1063         if ( !iMixer )
1064                 return -1;
1065
1066         return Px_GetMicrophoneBoost(iMixer);
1067 }
1068
1069 int pa_mic_boost_set(struct iaxc_audio_driver* d, int enable)
1070 {
1071         if ( !iMixer )
1072                 return -1;
1073
1074         return Px_SetMicrophoneBoost(iMixer, enable);
1075 }
1076
1077 /* initialize audio driver */
1078 static int _pa_initialize (struct iaxc_audio_driver *d, int sr)
1079 {
1080         PaError  err;
1081
1082         sample_rate = sr;
1083
1084         /* initialize portaudio */
1085         if ( paNoError != (err = Pa_Initialize()) )
1086         {
1087                 iaxci_usermsg(IAXC_TEXT_TYPE_ERROR, "Failed Pa_Initialize");
1088                 return err;
1089         }
1090
1091         /* scan devices */
1092         scan_devices(d);
1093
1094         /* setup methods */
1095         d->initialize = pa_initialize;
1096         d->destroy = pa_destroy;
1097         d->select_devices = pa_select_devices;
1098         d->selected_devices = pa_selected_devices;
1099         d->start = pa_start;
1100         d->stop = pa_stop;
1101         d->output = pa_output;
1102         d->input = pa_input;
1103         d->input_level_get = pa_input_level_get;
1104         d->input_level_set = pa_input_level_set;
1105         d->output_level_get = pa_output_level_get;
1106         d->output_level_set = pa_output_level_set;
1107         d->play_sound = pa_play_sound;
1108         d->stop_sound = pa_stop_sound;
1109         d->mic_boost_get = pa_mic_boost_get;
1110         d->mic_boost_set = pa_mic_boost_set;
1111
1112         /* setup private data stuff */
1113         selectedInput  = Pa_GetDefaultInputDevice();
1114         selectedOutput = Pa_GetDefaultOutputDevice();
1115         selectedRing   = Pa_GetDefaultOutputDevice();
1116         sounds = NULL;
1117         MUTEXINIT(&sound_lock);
1118
1119         rb_InitializeRingBuffer(&inRing, INRBSZ, inRingBuf);
1120         rb_InitializeRingBuffer(&outRing, OUTRBSZ, outRingBuf);
1121
1122         running = 0;
1123
1124         return 0;
1125 }
1126
1127 /* standard initialization:  Do the normal initialization, and then
1128    also initialize mixers and levels */
1129 int pa_initialize(struct iaxc_audio_driver *d, int sr)
1130 {
1131         _pa_initialize(d, sr);
1132
1133         /* TODO: Kludge alert. We only do the funny audio start-stop
1134          * business if iaxci_audio_output_mode is not set. This is a
1135          * hack to allow certain specific users of iaxclient to avoid
1136          * certain problems associated with portaudio initialization
1137          * hitting a deadlock condition.
1138          */
1139         if ( iaxci_audio_output_mode )
1140                 return 0;
1141
1142         /* start/stop audio, in order to initialize mixers and levels */
1143         pa_start(d);
1144         pa_stop(d);
1145
1146         return 0;
1147 }
1148
1149 /* alternate initialization:  delay mixer/level initialization until
1150    we actually start the device.  This is somewhat useful when you're about to start
1151    the device as soon as you've initialized it, and want to avoid the time it
1152    takes to start/stop the device before starting it again */
1153 int pa_initialize_deferred(struct iaxc_audio_driver *d, int sr)
1154 {
1155         _pa_initialize(d, sr);
1156         return 0;
1157 }
1158