Exemple #1
0
/** 
 * Device initialization: check device capability and open for recording.
 * 
 * @param sfreq [in] required sampling frequency.
 * @param dummy [in] a dummy data
 * 
 * @return TRUE on success, FALSE on failure.
 */
boolean
adin_mic_standby(int sfreq, void *dummy)
{
  PaError err;
  int frames_per_buffer, num_buffer;
  int latency;
  char *p;

  /* set cycle buffer length */
  cycle_buffer_len = INPUT_DELAY_SEC * sfreq;
  j_printerr("Audio cycle buffer length: %d bytes\n", cycle_buffer_len * sizeof(SP16));

  /* for safety... */
  if (sizeof(SP16) != paInt16) {
    j_error("SP16 != paInt16\n");
  }

  /* allocate and init */
  current = processed = 0;
  speech = (SP16 *)mymalloc(sizeof(SP16) * cycle_buffer_len);
  buffer_overflowed = FALSE;

  /* set buffer parameter*/
  if ((p = getenv("LATENCY_MSEC")) != NULL) {
    j_printerr("adin_mic_standby: get LATENCY_MSEC=%s\n", p);
    latency = atoi(p);
  } else {
    latency = MAX_FRAGMENT_MSEC;
  }
  frames_per_buffer = 256;
  num_buffer = sfreq * latency / (frames_per_buffer * 1000);
  j_printf("framesPerBuffer=%d, NumBuffers(guess)=%d (%d)\n",
	   frames_per_buffer, num_buffer, 
	   Pa_GetMinNumBuffers(frames_per_buffer, sfreq));
  j_printf("Audio I/O Latency = %d msec (data fragment = %d frames)\n",
	   (frames_per_buffer * num_buffer) * 1000 / sfreq, 
	   (frames_per_buffer * num_buffer));

  /* initialize device and open stream */
  err = Pa_Initialize();
  if (err != paNoError) {
    j_printerr("Error: %s\n", Pa_GetErrorText(err));
    return(FALSE);
  }

  err = Pa_OpenDefaultStream(&stream, 1, 0, paInt16, sfreq, 
			     frames_per_buffer, num_buffer, 
			     Callback, NULL);
  if (err != paNoError) {
    j_printerr("Error: %s\n", Pa_GetErrorText(err));
    return(FALSE);
  }

  return(TRUE);
}
Exemple #2
0
void Gear_AudioInput::initPortAudio()
{
  std::cout << "Opening PortAudio Stream..." << std::endl;
  
  if (_stream)
  {  
    Pa_AbortStream(_stream);
    Pa_CloseStream(_stream);
  }
  
  std::cout << Engine::signalInfo().sampleRate() << "hz " << std::endl;
  
  int framesPerBuffer = _settings.get(SETTING_FRAMES_PER_BUFFER)->valueInt();
  std::cout << "Frames per buffer: " << framesPerBuffer << std::endl;

  int nbBuffers = _settings.get(SETTING_NB_BUFFERS)->valueInt();
  //if nbBuffers is 0, let portaudio set the value
  if (!nbBuffers)
  {
      nbBuffers = Pa_GetMinNumBuffers(framesPerBuffer, Engine::signalInfo().sampleRate());
      _settings.get(SETTING_NB_BUFFERS)->valueInt(nbBuffers);
  }
  
  std::cout << "Number of buffers: " << nbBuffers << std::endl;

  _ringBufferSize = framesPerBuffer;

  _lBuffer.resize(_ringBufferSize);

  PaError err = Pa_OpenStream(&_stream,
                             Pa_GetDefaultInputDeviceID(),/* default input device*/
                             1,              //input
                             paFloat32,     
                             NULL,
                             paNoDevice,    //no output
                             0,             //mono          
                             paFloat32,     
                             NULL,
                             Engine::signalInfo().sampleRate(),
                             framesPerBuffer,
                             nbBuffers,              /* number of buffers, if zero then use default minimum*/
                             paClipOff,      /* we won't output out of range samples so don't bother clipping them*/
                             portAudioCallback,
                             this);


  if (err != paNoError)
    std::cout << Pa_GetErrorText(err) << std::endl;
  else
    std::cout << "Opening PortAudio Stream...done" << std::endl;

}
Exemple #3
0
static int open_audio(){
    /* this will open one circular audio stream */
    /* build on top of portaudio routines */
    /* implementation based on file pastreamio.c */

    int numSamples;
    int numBytes;

    int minNumBuffers;
    int numFrames;

    minNumBuffers = 2 * Pa_GetMinNumBuffers( FRAMES_PER_BUFFER, vi.rate );
    numFrames = minNumBuffers * FRAMES_PER_BUFFER;
    numFrames = RoundUpToNextPowerOf2( numFrames );

    numSamples = numFrames * vi.channels;
    numBytes = numSamples * sizeof(SAMPLE);

    samples = (SAMPLE *) malloc( numBytes );

    /* store our latency calculation here */
    latency_sec =  (double) numFrames / vi.rate / vi.channels;
    printf( "Latency: %.04f\n", latency_sec );

    err = OpenAudioStream( &aOutStream, vi.rate, PA_SAMPLE_TYPE,
                           (PASTREAMIO_WRITE | PASTREAMIO_STEREO) );
    if( err != paNoError ) goto error;
    return err;
error:
    CloseAudioStream( aOutStream );
    printf( "An error occured while opening the portaudio stream\n" );
    printf( "Error number: %d\n", err );
    printf( "Error message: %s\n", Pa_GetErrorText( err ) );
    return err;

}
Exemple #4
0
PaError PaHost_OpenStream( internalPortAudioStream   *past )
{
    PaError          result = paNoError;
    PaHostSoundControl *pahsc;
    unsigned int     minNumBuffers;
    internalPortAudioDevice *pad;
    DBUG(("PaHost_OpenStream() called.\n" ));

    /* Allocate and initialize host data. */
    pahsc = (PaHostSoundControl *) malloc(sizeof(PaHostSoundControl));
    if( pahsc == NULL )
    {
        result = paInsufficientMemory;
        goto error;
    }
    memset( pahsc, 0, sizeof(PaHostSoundControl) );
    past->past_DeviceData = (void *) pahsc;

    pahsc->pahsc_OutputHandle = BAD_DEVICE_ID; /* No device currently opened. */
    pahsc->pahsc_InputHandle = BAD_DEVICE_ID;
    pahsc->pahsc_IsAudioThreadValid = 0;
    pahsc->pahsc_IsWatchDogThreadValid = 0;

    /* Allocate native buffers. */
    pahsc->pahsc_BytesPerInputBuffer = past->past_FramesPerUserBuffer *
                                       past->past_NumInputChannels * sizeof(short);
    if( past->past_NumInputChannels > 0)
    {
        pahsc->pahsc_NativeInputBuffer = (short *) malloc(pahsc->pahsc_BytesPerInputBuffer);
        if( pahsc->pahsc_NativeInputBuffer == NULL )
        {
            result = paInsufficientMemory;
            goto error;
        }
    }
    pahsc->pahsc_BytesPerOutputBuffer = past->past_FramesPerUserBuffer *
                                        past->past_NumOutputChannels * sizeof(short);
    if( past->past_NumOutputChannels > 0)
    {
        pahsc->pahsc_NativeOutputBuffer = (short *) malloc(pahsc->pahsc_BytesPerOutputBuffer);
        if( pahsc->pahsc_NativeOutputBuffer == NULL )
        {
            result = paInsufficientMemory;
            goto error;
        }
    }

    /* DBUG(("PaHost_OpenStream: pahsc_MinFramesPerHostBuffer = %d\n", pahsc->pahsc_MinFramesPerHostBuffer )); */
    minNumBuffers = Pa_GetMinNumBuffers( past->past_FramesPerUserBuffer, past->past_SampleRate );
    past->past_NumUserBuffers = ( minNumBuffers > past->past_NumUserBuffers ) ? minNumBuffers : past->past_NumUserBuffers;

    pahsc->pahsc_InverseMicrosPerBuffer = past->past_SampleRate / (1000000.0 * past->past_FramesPerUserBuffer);
    DBUG(("past_SampleRate = %g\n", past->past_SampleRate ));
    DBUG(("past_FramesPerUserBuffer = %d\n", past->past_FramesPerUserBuffer ));
    DBUG(("pahsc_InverseMicrosPerBuffer = %g\n", pahsc->pahsc_InverseMicrosPerBuffer ));

    /* ------------------------- OPEN DEVICE -----------------------*/

    /* just output */
    if (past->past_OutputDeviceID == past->past_InputDeviceID)
    {

        if ((past->past_NumOutputChannels > 0) && (past->past_NumInputChannels > 0) )
        {
            pad = Pa_GetInternalDevice( past->past_OutputDeviceID );
            DBUG(("PaHost_OpenStream: attempt to open %s for O_RDWR\n", pad->pad_DeviceName ));

            /* dmazzoni: test it first in nonblocking mode to
               make sure the device is not busy */
            pahsc->pahsc_InputHandle = open(pad->pad_DeviceName,O_RDWR|O_NONBLOCK);
            if(pahsc->pahsc_InputHandle==-1)
            {
                ERR_RPT(("PaHost_OpenStream: could not open %s for O_RDWR\n", pad->pad_DeviceName ));
                result = paHostError;
                goto error;
            }
            close(pahsc->pahsc_InputHandle);

            pahsc->pahsc_OutputHandle = pahsc->pahsc_InputHandle =
                                            open(pad->pad_DeviceName,O_RDWR);
            if(pahsc->pahsc_InputHandle==-1)
            {
                ERR_RPT(("PaHost_OpenStream: could not open %s for O_RDWR\n", pad->pad_DeviceName ));
                result = paHostError;
                goto error;
            }
            Pa_SetLatency( pahsc->pahsc_OutputHandle,
                           past->past_NumUserBuffers, past->past_FramesPerUserBuffer,
                           past->past_NumOutputChannels );
            result = Pa_SetupDeviceFormat( pahsc->pahsc_OutputHandle,
                                           past->past_NumOutputChannels, (int)past->past_SampleRate );
        }
    }
    else
    {
        if (past->past_NumOutputChannels > 0)
        {
            pad = Pa_GetInternalDevice( past->past_OutputDeviceID );
            DBUG(("PaHost_OpenStream: attempt to open %s for O_WRONLY\n", pad->pad_DeviceName ));
            /* dmazzoni: test it first in nonblocking mode to
               make sure the device is not busy */
            pahsc->pahsc_OutputHandle = open(pad->pad_DeviceName,O_WRONLY|O_NONBLOCK);
            if(pahsc->pahsc_OutputHandle==-1)
            {
                ERR_RPT(("PaHost_OpenStream: could not open %s for O_WRONLY\n", pad->pad_DeviceName ));
                result = paHostError;
                goto error;
            }
            close(pahsc->pahsc_OutputHandle);

            pahsc->pahsc_OutputHandle = open(pad->pad_DeviceName,O_WRONLY);
            if(pahsc->pahsc_OutputHandle==-1)
            {
                ERR_RPT(("PaHost_OpenStream: could not open %s for O_WRONLY\n", pad->pad_DeviceName ));
                result = paHostError;
                goto error;
            }
            Pa_SetLatency( pahsc->pahsc_OutputHandle,
                           past->past_NumUserBuffers, past->past_FramesPerUserBuffer,
                           past->past_NumOutputChannels );
            result = Pa_SetupOutputDeviceFormat( pahsc->pahsc_OutputHandle,
                                           past->past_NumOutputChannels, (int)past->past_SampleRate );
        }

        if (past->past_NumInputChannels > 0)
        {
            pad = Pa_GetInternalDevice( past->past_InputDeviceID );
            DBUG(("PaHost_OpenStream: attempt to open %s for O_RDONLY\n", pad->pad_DeviceName ));
            /* dmazzoni: test it first in nonblocking mode to
               make sure the device is not busy */
            pahsc->pahsc_InputHandle = open(pad->pad_DeviceName,O_RDONLY|O_NONBLOCK);
            if(pahsc->pahsc_InputHandle==-1)
            {
                ERR_RPT(("PaHost_OpenStream: could not open %s for O_RDONLY\n", pad->pad_DeviceName ));
                result = paHostError;
                goto error;
            }
            close(pahsc->pahsc_InputHandle);

            pahsc->pahsc_InputHandle = open(pad->pad_DeviceName,O_RDONLY);
            if(pahsc->pahsc_InputHandle==-1)
            {
                ERR_RPT(("PaHost_OpenStream: could not open %s for O_RDONLY\n", pad->pad_DeviceName ));
                result = paHostError;
                goto error;
            }
            Pa_SetLatency( pahsc->pahsc_InputHandle, /* DH20010115 - was OutputHandle! */
                           past->past_NumUserBuffers, past->past_FramesPerUserBuffer,
                           past->past_NumInputChannels );
            result = Pa_SetupInputDeviceFormat( pahsc->pahsc_InputHandle,
                                           past->past_NumInputChannels, (int)past->past_SampleRate );
        }
    }


    DBUG(("PaHost_OpenStream: SUCCESS - result = %d\n", result ));
    return result;

error:
    ERR_RPT(("PaHost_OpenStream: ERROR - result = %d\n", result ));
    PaHost_CloseStream( past );
    return result;
}
Exemple #5
0
PaError PaHost_OpenStream( internalPortAudioStream   *past )
{
	HRESULT          hr;
	PaError          result = paNoError;
	PaHostSoundControl *pahsc;
	int              numBytes, maxChannels;
	unsigned int     minNumBuffers;
	internalPortAudioDevice *pad;
	DSoundWrapper   *dsw;
/* Allocate and initialize host data. */
	pahsc = (PaHostSoundControl *) PaHost_AllocateFastMemory(sizeof(PaHostSoundControl)); /* MEM */
	if( pahsc == NULL )
	{
		result = paInsufficientMemory;
		goto error;
	}
	memset( pahsc, 0, sizeof(PaHostSoundControl) );
	past->past_DeviceData = (void *) pahsc;
	pahsc->pahsc_TimerID = 0;
	dsw = &pahsc->pahsc_DSoundWrapper;
	DSW_Init( dsw );
/* Allocate native buffer. */
	maxChannels = ( past->past_NumOutputChannels > past->past_NumInputChannels ) ?
		past->past_NumOutputChannels : past->past_NumInputChannels;
	pahsc->pahsc_BytesPerBuffer = past->past_FramesPerUserBuffer * maxChannels * sizeof(short);
	if( maxChannels > 0 )
	{
		pahsc->pahsc_NativeBuffer = (short *) PaHost_AllocateFastMemory(pahsc->pahsc_BytesPerBuffer); /* MEM */
		if( pahsc->pahsc_NativeBuffer == NULL )
		{
			result = paInsufficientMemory;
			goto error;
		}
	}
	else
	{
		result = paInvalidChannelCount;
		goto error;
	}
	
	DBUG(("PaHost_OpenStream: pahsc_MinFramesPerHostBuffer = %d\n", pahsc->pahsc_MinFramesPerHostBuffer ));
	minNumBuffers = Pa_GetMinNumBuffers( past->past_FramesPerUserBuffer, past->past_SampleRate );
	past->past_NumUserBuffers = ( minNumBuffers > past->past_NumUserBuffers ) ? minNumBuffers : past->past_NumUserBuffers;
	numBytes = pahsc->pahsc_BytesPerBuffer * past->past_NumUserBuffers;
	if( numBytes < DSBSIZE_MIN )
	{
		result = paBufferTooSmall;
		goto error;
	}
	if( numBytes > DSBSIZE_MAX )
	{
		result = paBufferTooBig;
		goto error;
	}
	pahsc->pahsc_FramesPerDSBuffer = past->past_FramesPerUserBuffer * past->past_NumUserBuffers;
	{
		int msecLatency = (int) ((pahsc->pahsc_FramesPerDSBuffer * 1000) / past->past_SampleRate);
		PRINT(("PortAudio on DirectSound - Latency = %d frames, %d msec\n", pahsc->pahsc_FramesPerDSBuffer, msecLatency ));
	}
/* ------------------ OUTPUT */
	if( (past->past_OutputDeviceID >= 0) && (past->past_NumOutputChannels > 0) )
	{
		DBUG(("PaHost_OpenStream: deviceID = 0x%x\n", past->past_OutputDeviceID));
		pad = Pa_GetInternalDevice( past->past_OutputDeviceID );
		hr = DirectSoundCreate( pad->pad_lpGUID, &dsw->dsw_pDirectSound,   NULL );
/* If this fails, then try each output device until we find one that works. */
		if( hr != DS_OK )
		{
			int i;
			ERR_RPT(("Creation of requested Audio Output device '%s' failed.\n",
				((pad->pad_lpGUID == NULL) ? "Default" : pad->pad_Info.name) ));
			for( i=0; i<Pa_CountDevices(); i++ )
			{
				pad = Pa_GetInternalDevice( i );
				if( pad->pad_Info.maxOutputChannels >= past->past_NumOutputChannels )
				{
					DBUG(("Try device '%s' instead.\n", pad->pad_Info.name ));
					hr = DirectSoundCreate( pad->pad_lpGUID, &dsw->dsw_pDirectSound,   NULL );
					if( hr == DS_OK )
					{
						ERR_RPT(("Using device '%s' instead.\n", pad->pad_Info.name ));
						break;
					}
				}
			}
		}
		if( hr != DS_OK )
		{
			ERR_RPT(("PortAudio: DirectSoundCreate() failed!\n"));
			result = paHostError;
			sPaHostError = hr;
			goto error;
		}
		hr = DSW_InitOutputBuffer( dsw,
			(unsigned long) (past->past_SampleRate + 0.5),
			past->past_NumOutputChannels, numBytes );
		DBUG(("DSW_InitOutputBuffer() returns %x\n", hr));
		if( hr != DS_OK )
		{
			result = paHostError;
			sPaHostError = hr;
			goto error;
		}
		past->past_FrameCount = pahsc->pahsc_DSoundWrapper.dsw_FramesWritten;
	}
#if SUPPORT_AUDIO_CAPTURE
/* ------------------ INPUT */
	if( (past->past_InputDeviceID >= 0) && (past->past_NumInputChannels > 0) )
	{
		pad = Pa_GetInternalDevice( past->past_InputDeviceID );
		hr = DirectSoundCaptureCreate( pad->pad_lpGUID, &dsw->dsw_pDirectSoundCapture,   NULL );
/* If this fails, then try each input device until we find one that works. */
		if( hr != DS_OK )
		{
			int i;
			ERR_RPT(("Creation of requested Audio Capture device '%s' failed.\n",
				((pad->pad_lpGUID == NULL) ? "Default" : pad->pad_Info.name) ));
			for( i=0; i<Pa_CountDevices(); i++ )
			{
				pad = Pa_GetInternalDevice( i );
				if( pad->pad_Info.maxInputChannels >= past->past_NumInputChannels )
				{
					PRINT(("Try device '%s' instead.\n", pad->pad_Info.name ));
					hr = DirectSoundCaptureCreate( pad->pad_lpGUID, &dsw->dsw_pDirectSoundCapture,   NULL );
					if( hr == DS_OK ) break;
				}
			}
		}
		if( hr != DS_OK )
		{
			ERR_RPT(("PortAudio: DirectSoundCaptureCreate() failed!\n"));
			result = paHostError;
			sPaHostError = hr;
			goto error;
		}
		hr = DSW_InitInputBuffer( dsw,
			(unsigned long) (past->past_SampleRate + 0.5),
			past->past_NumInputChannels, numBytes );
		DBUG(("DSW_InitInputBuffer() returns %x\n", hr));
		if( hr != DS_OK )
		{
			ERR_RPT(("PortAudio: DSW_InitInputBuffer() returns %x\n", hr));
			result = paHostError;
			sPaHostError = hr;
			goto error;
		}
	}
#endif /* SUPPORT_AUDIO_CAPTURE */
	/* Calculate scalar used in CPULoad calculation. */ 
	{
		LARGE_INTEGER frequency;
		if( QueryPerformanceFrequency( &frequency ) == 0 )
		{
			pahsc->pahsc_InverseTicksPerUserBuffer = 0.0;
		}
		else
		{
			pahsc->pahsc_InverseTicksPerUserBuffer = past->past_SampleRate /
				( (double)frequency.QuadPart * past->past_FramesPerUserBuffer );
			DBUG(("pahsc_InverseTicksPerUserBuffer = %g\n", pahsc->pahsc_InverseTicksPerUserBuffer ));
		}
	}
	return result;
error:
	PaHost_CloseStream( past );
	return result;
}
Exemple #6
0
static int open_output(void)
{
	double rate;
	int n, nrates, include_enc, exclude_enc, ret;
	PaSampleFormat SampleFormat, nativeSampleFormats;
	
	if( dpm.name != NULL)
		ret = sscanf(dpm.name, "%d", &opt_pa_device_id);
	if (dpm.name == NULL || ret == 0 || ret == EOF)
		opt_pa_device_id = -2;
	
#ifdef AU_PORTAUDIO_DLL
#if PORTAUDIO_V19
  {
		if(&dpm == &portaudio_asio_play_mode){
			HostApiTypeId = paASIO;
		} else if(&dpm == &portaudio_win_ds_play_mode){
			HostApiTypeId = paDirectSound;
		} else if(&dpm == &portaudio_win_wmme_play_mode){
			HostApiTypeId = paMME;
		} else {
			return -1;
		}
		if(load_portaudio_dll(0))
				return -1;
  }
#else
  {
		if(&dpm == &portaudio_asio_play_mode){
			if(load_portaudio_dll(PA_DLL_ASIO))
				return -1;
		} else if(&dpm == &portaudio_win_ds_play_mode){
			if(load_portaudio_dll(PA_DLL_WIN_DS))
				return -1;
		} else if(&dpm == &portaudio_win_wmme_play_mode){
			if(load_portaudio_dll(PA_DLL_WIN_WMME))
				return -1;
		} else {
			return -1;
		}
  }
#endif
#endif
	/* if call twice Pa_OpenStream causes paDeviceUnavailable error  */
	if(pa_active == 1) return 0; 
	if(pa_active == 0){
		err = Pa_Initialize();
		if( err != paNoError ) goto error;
		pa_active = 1;
	}

	if (opt_pa_device_id == -1){
		print_device_list();
		goto error2;
	}
#ifdef PORTAUDIO_V19
#ifdef AU_PORTAUDIO_DLL
       {	
        PaHostApiIndex i, ApiCount;
	i = 0;
	ApiCount = Pa_GetHostApiCount();
	do{
		HostApiInfo=Pa_GetHostApiInfo(i);
		if( HostApiInfo->type == HostApiTypeId ) break;
		i++;
	}while ( i < ApiCount );
	if ( i == ApiCount ) goto error;
	
	DeviceIndex = HostApiInfo->defaultOutputDevice;
	if(DeviceIndex==paNoDevice) goto error;
        }
#else
	DeviceIndex = Pa_GetDefaultOutputDevice();
	if(DeviceIndex==paNoDevice) goto error;
#endif
	DeviceInfo = Pa_GetDeviceInfo( DeviceIndex);
	if(DeviceInfo==NULL) goto error;

	if(opt_pa_device_id != -2){
		const PaDeviceInfo *id_DeviceInfo;
    	id_DeviceInfo=Pa_GetDeviceInfo((PaDeviceIndex)opt_pa_device_id);
		if(id_DeviceInfo==NULL) goto error;
		if( DeviceInfo->hostApi == id_DeviceInfo->hostApi){
			DeviceIndex=(PaDeviceIndex)opt_pa_device_id;
			DeviceInfo = id_DeviceInfo;
		}
    }


	if (dpm.encoding & PE_24BIT) {
		SampleFormat = paInt24;
	}else if (dpm.encoding & PE_16BIT) {
		SampleFormat = paInt16;
	}else {
		SampleFormat = paInt8;
	}

	stereo = (dpm.encoding & PE_MONO) ? 1 : 2;
	data_nbyte = (dpm.encoding & PE_16BIT) ? 2 : 1;
	data_nbyte = (dpm.encoding & PE_24BIT) ? 3 : data_nbyte;
	
	pa_data.samplesToGo = 0;
	pa_data.bufpoint = pa_data.buf;
	pa_data.bufepoint = pa_data.buf;
//	firsttime = 1;
	numBuffers = 1; //Pa_GetMinNumBuffers( framesPerBuffer, dpm.rate );
	framesPerInBuffer = numBuffers * framesPerBuffer;
	if (framesPerInBuffer < 4096) framesPerInBuffer = 4096;
	bytesPerInBuffer = framesPerInBuffer * data_nbyte * stereo;

	/* set StreamParameters */
	StreamParameters.device = DeviceIndex;
	StreamParameters.channelCount = stereo;
	if(ctl->id_character != 'r' && ctl->id_character != 'A' && ctl->id_character != 'W' && ctl->id_character != 'P'){
		StreamParameters.suggestedLatency = DeviceInfo->defaultHighOutputLatency;
	}else{
		StreamParameters.suggestedLatency = DeviceInfo->defaultLowOutputLatency;
	}
	StreamParameters.hostApiSpecificStreamInfo = NULL;
	
	if( SampleFormat == paInt16){
		StreamParameters.sampleFormat = paInt16;
		if( paFormatIsSupported != Pa_IsFormatSupported( NULL , 
							&StreamParameters,(double) dpm.rate )){
			StreamParameters.sampleFormat = paInt32;
			conv16_32 = 1;
		} else {
			StreamParameters.sampleFormat = paInt16;
			conv16_32 = 0;
		}
	}else{
		StreamParameters.sampleFormat = SampleFormat;
	}
	err = Pa_IsFormatSupported( NULL ,
                             &StreamParameters,
							(double) dpm.rate );
	if ( err != paNoError) goto error;
	err = Pa_OpenStream(    
		& stream,			/* passes back stream pointer */
		NULL,			 	/* inputStreamParameters */
		&StreamParameters,	/* outputStreamParameters */
		(double) dpm.rate,	/* sample rate */
		paFramesPerBufferUnspecified,	/* frames per buffer */
		paFramesPerBufferUnspecified,	/* PaStreamFlags */
		paCallback,			/* specify our custom callback */
		&pa_data			/* pass our data through to callback */
		);
//		Pa_Sleeep(1);
	if ( err != paNoError) goto error;
	return 0;
	
#else
	if(opt_pa_device_id == -2){
		DeviceID = Pa_GetDefaultOutputDeviceID();
	    if(DeviceID==paNoDevice) goto error2;
	}else{
		DeviceID = opt_pa_device_id;
	}
	DeviceInfo = Pa_GetDeviceInfo( DeviceID);	
	if(DeviceInfo==NULL) goto error2;
	nativeSampleFormats = DeviceInfo->nativeSampleFormats;

	exclude_enc = PE_ULAW | PE_ALAW | PE_BYTESWAP;
	include_enc = PE_SIGNED;
	if (!(nativeSampleFormats & paInt16) && !(nativeSampleFormats & paInt32)) {exclude_enc |= PE_16BIT;}
	if (!(nativeSampleFormats & paInt24)) {exclude_enc |= PE_24BIT;}
    dpm.encoding = validate_encoding(dpm.encoding, include_enc, exclude_enc);

	if (dpm.encoding & PE_24BIT) {
		SampleFormat = paInt24;
	}else if (dpm.encoding & PE_16BIT) {
		if(nativeSampleFormats & paInt16) SampleFormat = paInt16;
		else{
			SampleFormat = paInt32;
			conv16_32 = 1;
		}
	}else {
		SampleFormat = paInt8;
	}

	stereo = (dpm.encoding & PE_MONO) ? 1 : 2;
	data_nbyte = (dpm.encoding & PE_16BIT) ? 2 : 1;
	data_nbyte = (dpm.encoding & PE_24BIT) ? 3 : data_nbyte;

	nrates = DeviceInfo->numSampleRates;
	if (nrates == -1) {	/* range supported */
		rate = dpm.rate;
		if (dpm.rate < DeviceInfo->sampleRates[0]) rate = DeviceInfo->sampleRates[0];
		if (dpm.rate > DeviceInfo->sampleRates[1]) rate = DeviceInfo->sampleRates[1];
	} else {
		rate = DeviceInfo->sampleRates[nrates-1];
		for (n = nrates - 1; n >= 0; n--) {	/* find nearest sample rate */
			if (dpm.rate <= DeviceInfo->sampleRates[n]) rate=DeviceInfo->sampleRates[n];
		}
	}
	dpm.rate = (int32)rate;
	
	pa_data.samplesToGo = 0;
	pa_data.bufpoint = pa_data.buf;
	pa_data.bufepoint = pa_data.buf;
//	firsttime = 1;
	numBuffers = Pa_GetMinNumBuffers( framesPerBuffer, dpm.rate );
	framesPerInBuffer = numBuffers * framesPerBuffer;
	if (framesPerInBuffer < 4096) framesPerInBuffer = 4096;
	bytesPerInBuffer = framesPerInBuffer * data_nbyte * stereo;
//	printf("%d\n",framesPerInBuffer);
//	printf("%d\n",dpm.rate);
	err = Pa_OpenDefaultStream(
    	&stream,        /* passes back stream pointer */
    	0,              /* no input channels */
    	stereo,              /* 2:stereo 1:mono output */
    	SampleFormat,      /* 24bit 16bit 8bit output */
		(double)dpm.rate,          /* sample rate */
    	framesPerBuffer,            /* frames per buffer */
    	numBuffers,              /* number of buffers, if zero then use default minimum */
    	paCallback, /* specify our custom callback */
    	&pa_data);   /* pass our data through to callback */
	if ( err != paNoError && err != paHostError) goto error;
	return 0;

#endif

error:
	ctl->cmsg(  CMSG_ERROR, VERB_NORMAL, "PortAudio error: %s\n", Pa_GetErrorText( err ) );
error2:
	Pa_Terminate(); pa_active = 0;
#ifdef AU_PORTAUDIO_DLL
#ifndef PORTAUDIO_V19
  free_portaudio_dll();
#endif
#endif

	return -1;
}
Exemple #7
0
/************************************************************
 * Opens a PortAudio stream with default characteristics.
 * Allocates PABLIO_Stream structure.
 *
 * flags parameter can be an ORed combination of:
 *    PABLIO_READ, PABLIO_WRITE, or PABLIO_READ_WRITE
 */
PaError OpenAudioStream( PABLIO_Stream **rwblPtr, double sampleRate,
                         PaSampleFormat format, int inchannels,
                         int outchannels, int framesperbuf, int nbuffers,
                         int indeviceno, int outdeviceno) /* MSP */
{
    long   bytesPerSample;
    long   doRead = 0;
    long   doWrite = 0;
    PaError err;
    PABLIO_Stream *aStream;
    long   minNumBuffers; 
    long   numFrames;

//#ifdef PA19
//    PaStreamParameters instreamparams, outstreamparams;  /* MSP */
//#endif

    /* fprintf(stderr,
        "open %lf fmt %d flags %d ch: %d fperbuf: %d nbuf: %d devs: %d %d\n",
           sampleRate, format, flags, nchannels,
           framesperbuf, nbuffers, indeviceno, outdeviceno); */

    if (indeviceno < 0)  /* MSP... */
    {

//#ifdef PA19
//        indeviceno = Pa_GetDefaultInputDevice();
//#else
        indeviceno = Pa_GetDefaultInputDeviceID();
//#endif
        fprintf(stderr, "using default input device number: %d\n", indeviceno);
    }
    if (outdeviceno < 0)
    {

//#ifdef PA19
//        outdeviceno = Pa_GetDefaultOutputDevice();
//#else
        outdeviceno = Pa_GetDefaultOutputDeviceID();
//#endif
        fprintf(stderr, "using default output device number: %d\n", outdeviceno);
    }
    /* fprintf(stderr, "nchan %d, flags %d, bufs %d, framesperbuf %d\n",
            nchannels, flags, nbuffers, framesperbuf); */
        /* ...MSP */

    /* Allocate PABLIO_Stream structure for caller. */
    aStream = (PABLIO_Stream *) malloc( sizeof(PABLIO_Stream) );
    if( aStream == NULL ) return paInsufficientMemory;
    memset( aStream, 0, sizeof(PABLIO_Stream) );

    /* Determine size of a sample. */
    bytesPerSample = Pa_GetSampleSize( format );
    if( bytesPerSample < 0 )
    {
        fprintf(stderr, "error bytes per sample: %i\n", bytesPerSample);	
		err = (PaError) bytesPerSample;
        goto error;
    }
    aStream->insamplesPerFrame = inchannels;  /* MSP */
    aStream->inbytesPerFrame = bytesPerSample * aStream->insamplesPerFrame;
    aStream->outsamplesPerFrame = outchannels;
    aStream->outbytesPerFrame = bytesPerSample * aStream->outsamplesPerFrame;

    /* Initialize PortAudio  */
    err = Pa_Initialize();
    if( err != paNoError ) goto error;


//#ifdef PA19
//    numFrames = nbuffers * framesperbuf; /* ...MSP */

//    instreamparams.device = indeviceno;   /* MSP... */
//    instreamparams.channelCount = inchannels;
//    instreamparams.sampleFormat = format;
//    instreamparams.suggestedLatency = nbuffers*framesperbuf/sampleRate;
//    instreamparams.hostApiSpecificStreamInfo = 0;
    
//    outstreamparams.device = outdeviceno;
//    outstreamparams.channelCount = outchannels;
//    outstreamparams.sampleFormat = format;
//    outstreamparams.suggestedLatency = nbuffers*framesperbuf/sampleRate;
//   outstreamparams.hostApiSpecificStreamInfo = 0;  /* ... MSP */

//#else
/* Warning: numFrames must be larger than amount of data processed per
  interrupt inside PA to prevent glitches. */  /* MSP */
    minNumBuffers = Pa_GetMinNumBuffers(framesperbuf, sampleRate);
    if (minNumBuffers > nbuffers)
        fprintf(stderr, "warning: number of buffers %d less than recommended minimum %d\n",  (int)nbuffers, (int)minNumBuffers);
//#endif

    numFrames = nbuffers * framesperbuf;
    /* fprintf(stderr, "numFrames %d\n", numFrames); */
    /* Initialize Ring Buffers */
    doRead = (inchannels != 0);
    doWrite = (outchannels != 0);
    if(doRead)
    {
        err = PABLIO_InitFIFO( &aStream->inFIFO, numFrames, aStream->inbytesPerFrame );
        if( err != paNoError )
		{
			fprintf(stderr, "error doRead PABLIO_InitFIFO \n");
			goto error;
		}
    }
    if(doWrite)
    {
        long numBytes;
        err = PABLIO_InitFIFO( &aStream->outFIFO, numFrames, aStream->outbytesPerFrame );
        if( err != paNoError ) {
			fprintf(stderr, "error doWrite PABLIO_InitFIFO \n");
			goto error;
			}
        /* Make Write FIFO appear full initially. */
        numBytes = RingBuffer_GetWriteAvailable( &aStream->outFIFO );
        RingBuffer_AdvanceWriteIndex( &aStream->outFIFO, numBytes );
    }

    /* Open a PortAudio stream that we will use to communicate with the underlying
     * audio drivers. */

//#ifdef PA19
 //   err = Pa_OpenStream(
//              &aStream->stream,
//              (doRead ? &instreamparams : 0),  /* MSP */
//              (doWrite ? &outstreamparams : 0),  /* MSP */
//             sampleRate,
 //             framesperbuf,  /* MSP */
 //             paNoFlag,      /* MSP -- portaudio will clip for us */
 //             blockingIOCallback,
//              aStream );
//#else
 //   err = Pa_OpenStream(
 //             &aStream->stream,
//              (doRead ? indeviceno : paNoDevice),  /* MSP */
//              (doRead ? aStream->insamplesPerFrame : 0 ),
//              format,
//              NULL,
//              (doWrite ? outdeviceno : paNoDevice),  /* MSP */
//              (doWrite ? aStream->outsamplesPerFrame : 0 ),
//              format,
//              NULL,
//              sampleRate,
//              framesperbuf,  /* MSP */
//              nbuffers,      /* MSP */
//              paNoFlag,      /* MSP -- portaudio will clip for us */
//              blockingIOCallback,
//              aStream );
// #endif
PortAudioStream   *stream;
err = Pa_OpenDefaultStream( 
	stream, 
	0,
	2, 
	paFloat32, 
	44100,  
	256, 
	0,  
	blockingIOCallback, 
	stream );


    if( err != paNoError ){
		fprintf(stderr, "error Pa_OpenStream \n");
		goto error;
	}
	
    err = Pa_StartStream( aStream->stream );
    if( err != paNoError )      /* MSP */
    {
        fprintf(stderr, "Pa_StartStream failed; closing audio stream...\n");
        CloseAudioStream( aStream );
        goto error;
    }

    *rwblPtr = aStream;
    return paNoError;

error:
    *rwblPtr = NULL;
    return err;
}
Exemple #8
0
void main( int argc, char **argv )
{
	PortAudioStream *stream;
	PaError err;
	paTestData data;
	int    i;
	int    go;
	int    numBuffers = 0;
	int    minBuffers = 0;
	int    framesPerBuffer;
	double sampleRate = 44100.0;
	char   str[256];
	printf("paminlat - Determine minimum latency for your computer.\n");
	printf("  usage:         paminlat {framesPerBuffer}\n");
	printf("  for example:   paminlat 256\n");
	printf("Adjust your stereo until you hear a smooth tone in each speaker.\n");
	printf("Then try to find the smallest number of buffers that still sounds smooth.\n");
	printf("Note that the sound will stop momentarily when you change the number of buffers.\n");
/* Get bufferSize from command line. */
	framesPerBuffer = ( argc > 1 ) ? atol( argv[1] ) : DEFAULT_BUFFER_SIZE;
	printf("Frames per buffer = %d\n", framesPerBuffer );
/* Initialise sinusoidal wavetable. */
	for( i=0; i<TABLE_SIZE; i++ )
	{
		data.sine[i] = (float) sin( ((double)i/(double)TABLE_SIZE) * M_PI * 2. );
	}
	data.left_phase = data.right_phase = 0;
	err = Pa_Initialize();
	if( err != paNoError ) goto error;
/* Ask PortAudio for the recommended minimum number of buffers. */
	numBuffers = minBuffers = Pa_GetMinNumBuffers( framesPerBuffer, sampleRate );
	printf("NumBuffers set to %d based on a call to Pa_GetMinNumBuffers()\n", numBuffers );
/* Try different numBuffers in a loop. */
	go = 1;
	while( go )
	{
		
		printf("Latency = framesPerBuffer * numBuffers = %d * %d = %d frames = %d msecs.\n",
			framesPerBuffer, numBuffers, framesPerBuffer*numBuffers,
			(int)((1000 * framesPerBuffer * numBuffers) / sampleRate) );
		err = Pa_OpenStream(
				&stream,
				paNoDevice,
				0,              /* no input */
				paFloat32,		/* 32 bit floating point input */
				NULL,
				Pa_GetDefaultOutputDeviceID(), /* default output device */
				2,              /* stereo output */
				paFloat32,      /* 32 bit floating point output */
				NULL,
				sampleRate,
				framesPerBuffer,/* 46 msec buffers */
				numBuffers,     /* number of buffers */
				paClipOff,      /* we won't output out of range samples so don't bother clipping them */
				paminlatCallback,
				&data );
		if( err != paNoError ) goto error;
		if( stream == NULL ) goto error;
/* Start audio. */
		err = Pa_StartStream( stream );
		if( err != paNoError ) goto error;
/* Ask user for a new number of buffers. */
		printf("\nMove windows around to see if the sound glitches.\n");
		printf("NumBuffers currently %d, enter new number, or 'q' to quit: ", numBuffers );
		gets( str );
		if( str[0] == 'q' ) go = 0;
		else
		{
			numBuffers = atol( str );
			if( numBuffers < minBuffers )
			{
				printf( "numBuffers below minimum of %d! Set to minimum!!!\n", minBuffers );
				numBuffers = minBuffers;
			}
		}
/* Stop sound until ENTER hit. */
		err = Pa_StopStream( stream );
		if( err != paNoError ) goto error;
		err = Pa_CloseStream( stream );
		if( err != paNoError ) goto error;
	}
	printf("A good setting for latency would be somewhat higher than\n");
	printf("the minimum latency that worked.\n");
	printf("PortAudio: Test finished.\n");
	Pa_Terminate();
	return;
error:
	Pa_Terminate();
	fprintf( stderr, "An error occured while using the portaudio stream\n" ); 
	fprintf( stderr, "Error number: %d\n", err );
	fprintf( stderr, "Error message: %s\n", Pa_GetErrorText( err ) );
}
Exemple #9
0
static int TestAdvance( int mode, PaDeviceID deviceID, double sampleRate,
                        int numChannels, PaSampleFormat format )
{
    PortAudioStream *stream = NULL;
    PaError result;
    PaQaData myData;
#define FRAMES_PER_BUFFER  (64)
    printf("------ TestAdvance: %s, device = %d, rate = %g, numChannels = %d, format = %d -------\n",
           ( mode == MODE_INPUT ) ? "INPUT" : "OUTPUT",
           deviceID, sampleRate, numChannels, format);
    fflush(stdout);
    /* Setup data for synthesis thread. */
    myData.framesLeft = (unsigned long) (sampleRate * 100); /* 100 seconds */
    myData.numChannels = numChannels;
    myData.mode = mode;
    myData.format = format;
    switch( format )
    {
    case paFloat32:
    case paInt32:
    case paInt24:
        myData.bytesPerSample = 4;
        break;
    case paPackedInt24:
        myData.bytesPerSample = 3;
        break;
    default:
        myData.bytesPerSample = 2;
        break;
    }
    EXPECT( ((result = Pa_OpenStream(
                           &stream,
                           ( mode == MODE_INPUT ) ? deviceID : paNoDevice,
                           ( mode == MODE_INPUT ) ? numChannels : 0,
                           format,
                           NULL,
                           ( mode == MODE_OUTPUT ) ? deviceID : paNoDevice,
                           ( mode == MODE_OUTPUT ) ? numChannels : 0,
                           format,
                           NULL,
                           sampleRate,
                           FRAMES_PER_BUFFER,     /* frames per buffer */
                           0,             /* number of buffers, if zero then use default minimum */
                           paClipOff,     /* we won't output out of range samples so don't bother clipping them */
                           QaCallback,
                           &myData )
             ) == 0) );
    if( stream )
    {
        PaTimestamp oldStamp, newStamp;
        unsigned long oldFrames;
        int minDelay = ( mode == MODE_INPUT ) ? 1000 : 400;
        int minNumBuffers = Pa_GetMinNumBuffers( FRAMES_PER_BUFFER, sampleRate );
        int msec = (int) ((minNumBuffers * 3 * 1000.0 * FRAMES_PER_BUFFER) / sampleRate);
        if( msec < minDelay ) msec = minDelay;
        printf("msec = %d\n", msec);  /**/
        EXPECT( ((result=Pa_StartStream( stream )) == 0) );
        /* Check to make sure PortAudio is advancing timeStamp. */
        result = paNoError;
        oldStamp = Pa_StreamTime(stream);
        fflush(stdout);
        Pa_Sleep(msec);
        newStamp = Pa_StreamTime(stream);
        printf("oldStamp = %g,newStamp = %g\n", oldStamp, newStamp ); /**/
        EXPECT( (oldStamp < newStamp) );
        /* Check to make sure callback is decrementing framesLeft. */
        oldFrames = myData.framesLeft;
        Pa_Sleep(msec);
        printf("oldFrames = %d, myData.framesLeft = %d\n", oldFrames,  myData.framesLeft ); /**/
        EXPECT( (oldFrames > myData.framesLeft) );
        EXPECT( ((result=Pa_CloseStream( stream )) == 0) );
        stream = NULL;
    }
error:
    if( stream != NULL ) Pa_CloseStream( stream );
    fflush(stdout);
    return result;
}
Exemple #10
0
bool AudioIO::OpenDevice()
{
   PaError         error;
   int             numPortAudioBuffers;
   int             recDeviceNum;
   int             playDeviceNum;
   PaSampleFormat  paFormat;
   wxString        recDevice;
   wxString        playDevice;

   numPortAudioBuffers = Pa_GetMinNumBuffers(mBufferSize, mRate);

   if (mNumInChannels>0)
      numPortAudioBuffers *= 2;

   recDeviceNum = Pa_GetDefaultInputDeviceID();
   playDeviceNum = Pa_GetDefaultOutputDeviceID();

   recDevice = gPrefs->Read("/AudioIO/RecordingDevice", "");
   playDevice = gPrefs->Read("/AudioIO/PlaybackDevice", "");

   mFormat = (sampleFormat)gPrefs->Read("/AudioIO/SampleFormat", floatSample);

   switch(mFormat) {
   case floatSample:
      paFormat = paFloat32;
      break;
   case int16Sample:
      paFormat = paInt16;
      break;
   default:
      // Debug message only
      printf("Cannot output this sample format using PortAudio\n");
      return false;
   }

   for(int j=0; j<Pa_CountDevices(); j++) {
      const PaDeviceInfo* info = Pa_GetDeviceInfo(j);
      if (info->name == playDevice && info->maxOutputChannels > 0)
         playDeviceNum = j;
      if (info->name == recDevice && info->maxInputChannels > 0)
         recDeviceNum = j;
   }

   if (mNumOutChannels<=0)
      playDeviceNum = paNoDevice;
   if (mNumInChannels<=0)
      recDeviceNum = paNoDevice;

   error = Pa_OpenStream(&mPortStream,
                         recDeviceNum,
                         mNumInChannels,
                         paFormat,
                         NULL, /* inputDriverInfo */
                         playDeviceNum,
                         mNumOutChannels,
                         paFormat,
                         NULL,
                         mRate,
                         (unsigned long)mBufferSize,
                         (unsigned long)numPortAudioBuffers,
                         paClipOff | paDitherOff,
                         audacityAudioCallback,
                         NULL);

   return (mPortStream != NULL && error == paNoError);
}
Exemple #11
0
/************************************************************
 * Opens a PortAudio stream with default characteristics.
 * Allocates PASTREAMIO_Stream structure.
 *
 * flags parameter can be an ORed combination of:
 *    PABLIO_WRITE, 
 *    and either PABLIO_MONO or PABLIO_STEREO
 */
PaError OpenAudioStream( PASTREAMIO_Stream **rwblPtr, double sampleRate,
                         PaSampleFormat format, long flags )
{
    long   bytesPerSample;
    long   doWrite = 0;
    PaError err;
    PASTREAMIO_Stream *aStream;
    long   minNumBuffers;
    long   numFrames;

    /* Allocate PASTREAMIO_Stream structure for caller. */
    aStream = (PASTREAMIO_Stream *) malloc( sizeof(PASTREAMIO_Stream) );
    if( aStream == NULL ) return paInsufficientMemory;
    memset( aStream, 0, sizeof(PASTREAMIO_Stream) );

    /* Determine size of a sample. */
    bytesPerSample = Pa_GetSampleSize( format );
    if( bytesPerSample < 0 )
    {
        err = (PaError) bytesPerSample;
        goto error;
    }
    aStream->samplesPerFrame = ((flags&PASTREAMIO_MONO) != 0) ? 1 : 2;
    aStream->bytesPerFrame = bytesPerSample * aStream->samplesPerFrame;

    /* Initialize PortAudio  */
    err = Pa_Initialize();
    if( err != paNoError ) goto error;

    /* Warning: numFrames must be larger than amount of data processed per interrupt
     *    inside PA to prevent glitches. Just to be safe, adjust size upwards.
     */
    minNumBuffers = 2 * Pa_GetMinNumBuffers( FRAMES_PER_BUFFER, sampleRate );
    numFrames = minNumBuffers * FRAMES_PER_BUFFER;
    numFrames = RoundUpToNextPowerOf2( numFrames );

    /* Initialize Ring Buffer */
    doWrite = ((flags & PASTREAMIO_WRITE) != 0);

    if(doWrite)
    {
        err = PASTREAMIO_InitFIFO( &aStream->outFIFO, numFrames, aStream->bytesPerFrame );
        if( err != paNoError ) goto error;
        /* Make Write FIFO appear full initially. 
        numBytes = RingBuffer_GetWriteAvailable( &aStream->outFIFO );
        RingBuffer_AdvanceWriteIndex( &aStream->outFIFO, numBytes );*/
    }

    /* Open a PortAudio stream that we will use to communicate with the underlying
     * audio drivers. */
    err = Pa_OpenStream(
              &aStream->stream,
              paNoDevice,
              0 ,
              format,
              NULL,
              Pa_GetDefaultOutputDeviceID() ,
              aStream->samplesPerFrame ,
              format,
              NULL,
              sampleRate,
              FRAMES_PER_BUFFER,
              minNumBuffers,
              paClipOff,       /* we won't output out of range samples so don't bother clipping them */
              audioIOCallback,
              aStream );
    if( err != paNoError ) goto error;

    *rwblPtr = aStream;
    return paNoError;

error:
    CloseAudioStream( aStream );
    *rwblPtr = NULL;
    return err;
}