static int load_ambdec_speakers(AmbDecConf *conf, FILE *f, char **buffer, size_t *maxlen, char **saveptr) { ALuint cur = 0; while(cur < conf->NumSpeakers) { const char *cmd = my_strtok_r(NULL, " \t", saveptr); if(!cmd) { char *line = read_clipped_line(f, buffer, maxlen); if(!line) { ERR("Unexpected end of file\n"); return 0; } cmd = my_strtok_r(line, " \t", saveptr); } if(strcmp(cmd, "add_spkr") == 0) { const char *name = my_strtok_r(NULL, " \t", saveptr); const char *dist = my_strtok_r(NULL, " \t", saveptr); const char *az = my_strtok_r(NULL, " \t", saveptr); const char *elev = my_strtok_r(NULL, " \t", saveptr); const char *conn = my_strtok_r(NULL, " \t", saveptr); if(!name) WARN("Name not specified for speaker %u\n", cur+1); else al_string_copy_cstr(&conf->Speakers[cur].Name, name); if(!dist) WARN("Distance not specified for speaker %u\n", cur+1); else read_float(&conf->Speakers[cur].Distance, dist); if(!az) WARN("Azimuth not specified for speaker %u\n", cur+1); else read_float(&conf->Speakers[cur].Azimuth, az); if(!elev) WARN("Elevation not specified for speaker %u\n", cur+1); else read_float(&conf->Speakers[cur].Elevation, elev); if(!conn) TRACE("Connection not specified for speaker %u\n", cur+1); else al_string_copy_cstr(&conf->Speakers[cur].Connection, conn); cur++; } else { ERR("Unexpected speakers command: %s\n", cmd); return 0; } cmd = my_strtok_r(NULL, " \t", saveptr); if(cmd) { ERR("Unexpected junk on line: %s\n", cmd); return 0; } } return 1; }
static ALCenum sndio_open_playback(ALCdevice *device, const ALCchar *deviceName) { sndio_data *data; if(!deviceName) deviceName = sndio_device; else if(strcmp(deviceName, sndio_device) != 0) return ALC_INVALID_VALUE; data = calloc(1, sizeof(*data)); data->killNow = 0; data->sndHandle = sio_open(NULL, SIO_PLAY, 0); if(data->sndHandle == NULL) { free(data); ERR("Could not open device\n"); return ALC_INVALID_VALUE; } al_string_copy_cstr(&device->DeviceName, deviceName); device->ExtraData = data; return ALC_NO_ERROR; }
static ALCenum opensl_open_playback(ALCdevice *Device, const ALCchar *deviceName) { osl_data *data = NULL; SLresult result; if(!deviceName) deviceName = opensl_device; else if(strcmp(deviceName, opensl_device) != 0) return ALC_INVALID_VALUE; data = calloc(1, sizeof(*data)); if(!data) return ALC_OUT_OF_MEMORY; // create engine result = slCreateEngine(&data->engineObject, 0, NULL, 0, NULL, NULL); PRINTERR(result, "slCreateEngine"); if(SL_RESULT_SUCCESS == result) { result = VCALL(data->engineObject,Realize)(SL_BOOLEAN_FALSE); PRINTERR(result, "engine->Realize"); } if(SL_RESULT_SUCCESS == result) { result = VCALL(data->engineObject,GetInterface)(SL_IID_ENGINE, &data->engine); PRINTERR(result, "engine->GetInterface"); } if(SL_RESULT_SUCCESS == result) { result = VCALL(data->engine,CreateOutputMix)(&data->outputMix, 0, NULL, NULL); PRINTERR(result, "engine->CreateOutputMix"); } if(SL_RESULT_SUCCESS == result) { result = VCALL(data->outputMix,Realize)(SL_BOOLEAN_FALSE); PRINTERR(result, "outputMix->Realize"); } if(SL_RESULT_SUCCESS != result) { if(data->outputMix != NULL) VCALL0(data->outputMix,Destroy)(); data->outputMix = NULL; if(data->engineObject != NULL) VCALL0(data->engineObject,Destroy)(); data->engineObject = NULL; data->engine = NULL; free(data); return ALC_INVALID_VALUE; } al_string_copy_cstr(&Device->DeviceName, deviceName); Device->ExtraData = data; return ALC_NO_ERROR; }
static ALCenum qsa_open_playback(ALCdevice* device, const ALCchar* deviceName) { qsa_data *data; int card, dev; int status; data = (qsa_data*)calloc(1, sizeof(qsa_data)); if(data == NULL) return ALC_OUT_OF_MEMORY; if(!deviceName) deviceName = qsaDevice; if(strcmp(deviceName, qsaDevice) == 0) status = snd_pcm_open_preferred(&data->pcmHandle, &card, &dev, SND_PCM_OPEN_PLAYBACK); else { const DevMap *iter; if(VECTOR_SIZE(DeviceNameMap) == 0) deviceList(SND_PCM_CHANNEL_PLAYBACK, &DeviceNameMap); #define MATCH_DEVNAME(iter) ((iter)->name && strcmp(deviceName, (iter)->name)==0) VECTOR_FIND_IF(iter, const DevMap, DeviceNameMap, MATCH_DEVNAME); #undef MATCH_DEVNAME if(iter == VECTOR_ITER_END(DeviceNameMap)) { free(data); return ALC_INVALID_DEVICE; } status = snd_pcm_open(&data->pcmHandle, iter->card, iter->dev, SND_PCM_OPEN_PLAYBACK); } if(status < 0) { free(data); return ALC_INVALID_DEVICE; } data->audio_fd = snd_pcm_file_descriptor(data->pcmHandle, SND_PCM_CHANNEL_PLAYBACK); if(data->audio_fd < 0) { snd_pcm_close(data->pcmHandle); free(data); return ALC_INVALID_DEVICE; } al_string_copy_cstr(&device->DeviceName, deviceName); device->ExtraData = data; return ALC_NO_ERROR; }
static ALCenum ca_open_playback(ALCdevice *device, const ALCchar *deviceName) { ComponentDescription desc; Component comp; ca_data *data; OSStatus err; if(!deviceName) deviceName = ca_device; else if(strcmp(deviceName, ca_device) != 0) return ALC_INVALID_VALUE; /* open the default output unit */ desc.componentType = kAudioUnitType_Output; desc.componentSubType = kAudioUnitSubType_DefaultOutput; desc.componentManufacturer = kAudioUnitManufacturer_Apple; desc.componentFlags = 0; desc.componentFlagsMask = 0; comp = FindNextComponent(NULL, &desc); if(comp == NULL) { ERR("FindNextComponent failed\n"); return ALC_INVALID_VALUE; } data = calloc(1, sizeof(*data)); err = OpenAComponent(comp, &data->audioUnit); if(err != noErr) { ERR("OpenAComponent failed\n"); free(data); return ALC_INVALID_VALUE; } /* init and start the default audio unit... */ err = AudioUnitInitialize(data->audioUnit); if(err != noErr) { ERR("AudioUnitInitialize failed\n"); CloseComponent(data->audioUnit); free(data); return ALC_INVALID_VALUE; } al_string_copy_cstr(&device->DeviceName, deviceName); device->ExtraData = data; return ALC_NO_ERROR; }
static BOOL CALLBACK DSoundEnumDevices(GUID *guid, const WCHAR *desc, const WCHAR* UNUSED(drvname), void *data) { vector_DevMap *devices = data; OLECHAR *guidstr = NULL; DevMap entry; HRESULT hr; int count; if(!guid) return TRUE; AL_STRING_INIT(entry.name); count = 0; while(1) { const DevMap *iter; al_string_copy_cstr(&entry.name, DEVNAME_HEAD); al_string_append_wcstr(&entry.name, desc); if(count != 0) { char str[64]; snprintf(str, sizeof(str), " #%d", count+1); al_string_append_cstr(&entry.name, str); } #define MATCH_ENTRY(i) (al_string_cmp(entry.name, (i)->name) == 0) VECTOR_FIND_IF(iter, const DevMap, *devices, MATCH_ENTRY); if(iter == VECTOR_END(*devices)) break; #undef MATCH_ENTRY count++; } entry.guid = *guid; hr = StringFromCLSID(guid, &guidstr); if(SUCCEEDED(hr)) { TRACE("Got device \"%s\", GUID \"%ls\"\n", al_string_get_cstr(entry.name), guidstr); CoTaskMemFree(guidstr); } VECTOR_PUSH_BACK(*devices, entry); return TRUE; }
static void ProbeCaptureDevices(void) { ALuint numdevs; ALuint i; clear_devlist(&CaptureDevices); numdevs = waveInGetNumDevs(); VECTOR_RESERVE(CaptureDevices, numdevs); for(i = 0;i < numdevs;i++) { WAVEINCAPSW WaveCaps; const al_string *iter; al_string dname; AL_STRING_INIT(dname); if(waveInGetDevCapsW(i, &WaveCaps, sizeof(WaveCaps)) == MMSYSERR_NOERROR) { ALuint count = 0; while(1) { al_string_copy_cstr(&dname, DEVNAME_HEAD); al_string_append_wcstr(&dname, WaveCaps.szPname); if(count != 0) { char str[64]; snprintf(str, sizeof(str), " #%d", count+1); al_string_append_cstr(&dname, str); } count++; #define MATCH_ENTRY(i) (al_string_cmp(dname, *(i)) == 0) VECTOR_FIND_IF(iter, const al_string, CaptureDevices, MATCH_ENTRY); if(iter == VECTOR_END(CaptureDevices)) break; #undef MATCH_ENTRY } TRACE("Got device \"%s\", ID %u\n", al_string_get_cstr(dname), i); } VECTOR_PUSH_BACK(CaptureDevices, dname); } }
static ALCenum ca_open_capture(ALCdevice *device, const ALCchar *deviceName) { AudioStreamBasicDescription requestedFormat; // The application requested format AudioStreamBasicDescription hardwareFormat; // The hardware format AudioStreamBasicDescription outputFormat; // The AudioUnit output format AURenderCallbackStruct input; ComponentDescription desc; AudioDeviceID inputDevice; UInt32 outputFrameCount; UInt32 propertySize; UInt32 enableIO; Component comp; ca_data *data; OSStatus err; desc.componentType = kAudioUnitType_Output; desc.componentSubType = kAudioUnitSubType_HALOutput; desc.componentManufacturer = kAudioUnitManufacturer_Apple; desc.componentFlags = 0; desc.componentFlagsMask = 0; // Search for component with given description comp = FindNextComponent(NULL, &desc); if(comp == NULL) { ERR("FindNextComponent failed\n"); return ALC_INVALID_VALUE; } data = calloc(1, sizeof(*data)); device->ExtraData = data; // Open the component err = OpenAComponent(comp, &data->audioUnit); if(err != noErr) { ERR("OpenAComponent failed\n"); goto error; } // Turn off AudioUnit output enableIO = 0; err = AudioUnitSetProperty(data->audioUnit, kAudioOutputUnitProperty_EnableIO, kAudioUnitScope_Output, 0, &enableIO, sizeof(ALuint)); if(err != noErr) { ERR("AudioUnitSetProperty failed\n"); goto error; } // Turn on AudioUnit input enableIO = 1; err = AudioUnitSetProperty(data->audioUnit, kAudioOutputUnitProperty_EnableIO, kAudioUnitScope_Input, 1, &enableIO, sizeof(ALuint)); if(err != noErr) { ERR("AudioUnitSetProperty failed\n"); goto error; } // Get the default input device propertySize = sizeof(AudioDeviceID); err = AudioHardwareGetProperty(kAudioHardwarePropertyDefaultInputDevice, &propertySize, &inputDevice); if(err != noErr) { ERR("AudioHardwareGetProperty failed\n"); goto error; } if(inputDevice == kAudioDeviceUnknown) { ERR("No input device found\n"); goto error; } // Track the input device err = AudioUnitSetProperty(data->audioUnit, kAudioOutputUnitProperty_CurrentDevice, kAudioUnitScope_Global, 0, &inputDevice, sizeof(AudioDeviceID)); if(err != noErr) { ERR("AudioUnitSetProperty failed\n"); goto error; } // set capture callback input.inputProc = ca_capture_callback; input.inputProcRefCon = device; err = AudioUnitSetProperty(data->audioUnit, kAudioOutputUnitProperty_SetInputCallback, kAudioUnitScope_Global, 0, &input, sizeof(AURenderCallbackStruct)); if(err != noErr) { ERR("AudioUnitSetProperty failed\n"); goto error; } // Initialize the device err = AudioUnitInitialize(data->audioUnit); if(err != noErr) { ERR("AudioUnitInitialize failed\n"); goto error; } // Get the hardware format propertySize = sizeof(AudioStreamBasicDescription); err = AudioUnitGetProperty(data->audioUnit, kAudioUnitProperty_StreamFormat, kAudioUnitScope_Input, 1, &hardwareFormat, &propertySize); if(err != noErr || propertySize != sizeof(AudioStreamBasicDescription)) { ERR("AudioUnitGetProperty failed\n"); goto error; } // Set up the requested format description switch(device->FmtType) { case DevFmtUByte: requestedFormat.mBitsPerChannel = 8; requestedFormat.mFormatFlags = kAudioFormatFlagIsPacked; break; case DevFmtShort: requestedFormat.mBitsPerChannel = 16; requestedFormat.mFormatFlags = kAudioFormatFlagIsSignedInteger | kAudioFormatFlagsNativeEndian | kAudioFormatFlagIsPacked; break; case DevFmtInt: requestedFormat.mBitsPerChannel = 32; requestedFormat.mFormatFlags = kAudioFormatFlagIsSignedInteger | kAudioFormatFlagsNativeEndian | kAudioFormatFlagIsPacked; break; case DevFmtFloat: requestedFormat.mBitsPerChannel = 32; requestedFormat.mFormatFlags = kAudioFormatFlagIsPacked; break; case DevFmtByte: case DevFmtUShort: case DevFmtUInt: ERR("%s samples not supported\n", DevFmtTypeString(device->FmtType)); goto error; } switch(device->FmtChans) { case DevFmtMono: requestedFormat.mChannelsPerFrame = 1; break; case DevFmtStereo: requestedFormat.mChannelsPerFrame = 2; break; case DevFmtQuad: case DevFmtX51: case DevFmtX51Side: case DevFmtX61: case DevFmtX71: ERR("%s not supported\n", DevFmtChannelsString(device->FmtChans)); goto error; } requestedFormat.mBytesPerFrame = requestedFormat.mChannelsPerFrame * requestedFormat.mBitsPerChannel / 8; requestedFormat.mBytesPerPacket = requestedFormat.mBytesPerFrame; requestedFormat.mSampleRate = device->Frequency; requestedFormat.mFormatID = kAudioFormatLinearPCM; requestedFormat.mReserved = 0; requestedFormat.mFramesPerPacket = 1; // save requested format description for later use data->format = requestedFormat; data->frameSize = FrameSizeFromDevFmt(device->FmtChans, device->FmtType); // Use intermediate format for sample rate conversion (outputFormat) // Set sample rate to the same as hardware for resampling later outputFormat = requestedFormat; outputFormat.mSampleRate = hardwareFormat.mSampleRate; // Determine sample rate ratio for resampling data->sampleRateRatio = outputFormat.mSampleRate / device->Frequency; // The output format should be the requested format, but using the hardware sample rate // This is because the AudioUnit will automatically scale other properties, except for sample rate err = AudioUnitSetProperty(data->audioUnit, kAudioUnitProperty_StreamFormat, kAudioUnitScope_Output, 1, (void *)&outputFormat, sizeof(outputFormat)); if(err != noErr) { ERR("AudioUnitSetProperty failed\n"); goto error; } // Set the AudioUnit output format frame count outputFrameCount = device->UpdateSize * data->sampleRateRatio; err = AudioUnitSetProperty(data->audioUnit, kAudioUnitProperty_MaximumFramesPerSlice, kAudioUnitScope_Output, 0, &outputFrameCount, sizeof(outputFrameCount)); if(err != noErr) { ERR("AudioUnitSetProperty failed: %d\n", err); goto error; } // Set up sample converter err = AudioConverterNew(&outputFormat, &requestedFormat, &data->audioConverter); if(err != noErr) { ERR("AudioConverterNew failed: %d\n", err); goto error; } // Create a buffer for use in the resample callback data->resampleBuffer = malloc(device->UpdateSize * data->frameSize * data->sampleRateRatio); // Allocate buffer for the AudioUnit output data->bufferList = allocate_buffer_list(outputFormat.mChannelsPerFrame, device->UpdateSize * data->frameSize * data->sampleRateRatio); if(data->bufferList == NULL) goto error; data->ring = CreateRingBuffer(data->frameSize, (device->UpdateSize * data->sampleRateRatio) * device->NumUpdates); if(data->ring == NULL) goto error; al_string_copy_cstr(&device->DeviceName, deviceName); return ALC_NO_ERROR; error: DestroyRingBuffer(data->ring); free(data->resampleBuffer); destroy_buffer_list(data->bufferList); if(data->audioConverter) AudioConverterDispose(data->audioConverter); if(data->audioUnit) CloseComponent(data->audioUnit); free(data); device->ExtraData = NULL; return ALC_INVALID_VALUE; }
static void probe_devices(snd_pcm_stream_t stream, vector_DevMap *DeviceList) { const char *main_prefix = "plughw:"; snd_ctl_t *handle; snd_ctl_card_info_t *info; snd_pcm_info_t *pcminfo; int card, err, dev; DevMap entry; clear_devlist(DeviceList); snd_ctl_card_info_malloc(&info); snd_pcm_info_malloc(&pcminfo); AL_STRING_INIT(entry.name); AL_STRING_INIT(entry.device_name); al_string_copy_cstr(&entry.name, alsaDevice); al_string_copy_cstr(&entry.device_name, GetConfigValue(NULL, "alsa", (stream==SND_PCM_STREAM_PLAYBACK) ? "device" : "capture", "default")); VECTOR_PUSH_BACK(*DeviceList, entry); card = -1; if((err=snd_card_next(&card)) < 0) ERR("Failed to find a card: %s\n", snd_strerror(err)); ConfigValueStr(NULL, "alsa", prefix_name(stream), &main_prefix); while(card >= 0) { const char *card_prefix = main_prefix; const char *cardname, *cardid; char name[256]; snprintf(name, sizeof(name), "hw:%d", card); if((err = snd_ctl_open(&handle, name, 0)) < 0) { ERR("control open (hw:%d): %s\n", card, snd_strerror(err)); goto next_card; } if((err = snd_ctl_card_info(handle, info)) < 0) { ERR("control hardware info (hw:%d): %s\n", card, snd_strerror(err)); snd_ctl_close(handle); goto next_card; } cardname = snd_ctl_card_info_get_name(info); cardid = snd_ctl_card_info_get_id(info); snprintf(name, sizeof(name), "%s-%s", prefix_name(stream), cardid); ConfigValueStr(NULL, "alsa", name, &card_prefix); dev = -1; while(1) { const char *device_prefix = card_prefix; const char *devname; char device[128]; if(snd_ctl_pcm_next_device(handle, &dev) < 0) ERR("snd_ctl_pcm_next_device failed\n"); if(dev < 0) break; snd_pcm_info_set_device(pcminfo, dev); snd_pcm_info_set_subdevice(pcminfo, 0); snd_pcm_info_set_stream(pcminfo, stream); if((err = snd_ctl_pcm_info(handle, pcminfo)) < 0) { if(err != -ENOENT) ERR("control digital audio info (hw:%d): %s\n", card, snd_strerror(err)); continue; } devname = snd_pcm_info_get_name(pcminfo); snprintf(name, sizeof(name), "%s-%s-%d", prefix_name(stream), cardid, dev); ConfigValueStr(NULL, "alsa", name, &device_prefix); snprintf(name, sizeof(name), "%s, %s (CARD=%s,DEV=%d)", cardname, devname, cardid, dev); snprintf(device, sizeof(device), "%sCARD=%s,DEV=%d", device_prefix, cardid, dev); TRACE("Got device \"%s\", \"%s\"\n", name, device); AL_STRING_INIT(entry.name); AL_STRING_INIT(entry.device_name); al_string_copy_cstr(&entry.name, name); al_string_copy_cstr(&entry.device_name, device); VECTOR_PUSH_BACK(*DeviceList, entry); } snd_ctl_close(handle); next_card: if(snd_card_next(&card) < 0) { ERR("snd_card_next failed\n"); break; } } snd_pcm_info_free(pcminfo); snd_ctl_card_info_free(info); }
static ALCenum qsa_open_capture(ALCdevice* device, const ALCchar* deviceName) { qsa_data *data; int card, dev; int format=-1; int status; data=(qsa_data*)calloc(1, sizeof(qsa_data)); if (data==NULL) { return ALC_OUT_OF_MEMORY; } if(!deviceName) deviceName = qsaDevice; if(strcmp(deviceName, qsaDevice) == 0) status = snd_pcm_open_preferred(&data->pcmHandle, &card, &dev, SND_PCM_OPEN_CAPTURE); else { const DevMap *iter; if(VECTOR_SIZE(CaptureNameMap) == 0) deviceList(SND_PCM_CHANNEL_CAPTURE, &CaptureNameMap); #define MATCH_DEVNAME(iter) ((iter)->name && strcmp(deviceName, (iter)->name)==0) VECTOR_FIND_IF(iter, const DevMap, CaptureNameMap, MATCH_DEVNAME); #undef MATCH_DEVNAME if(iter == VECTOR_ITER_END(CaptureNameMap)) { free(data); return ALC_INVALID_DEVICE; } status = snd_pcm_open(&data->pcmHandle, iter->card, iter->dev, SND_PCM_OPEN_CAPTURE); } if(status < 0) { free(data); return ALC_INVALID_DEVICE; } data->audio_fd = snd_pcm_file_descriptor(data->pcmHandle, SND_PCM_CHANNEL_CAPTURE); if(data->audio_fd < 0) { snd_pcm_close(data->pcmHandle); free(data); return ALC_INVALID_DEVICE; } al_string_copy_cstr(&device->DeviceName, deviceName); device->ExtraData = data; switch (device->FmtType) { case DevFmtByte: format=SND_PCM_SFMT_S8; break; case DevFmtUByte: format=SND_PCM_SFMT_U8; break; case DevFmtShort: format=SND_PCM_SFMT_S16_LE; break; case DevFmtUShort: format=SND_PCM_SFMT_U16_LE; break; case DevFmtInt: format=SND_PCM_SFMT_S32_LE; break; case DevFmtUInt: format=SND_PCM_SFMT_U32_LE; break; case DevFmtFloat: format=SND_PCM_SFMT_FLOAT_LE; break; } /* we actually don't want to block on reads */ snd_pcm_nonblock_mode(data->pcmHandle, 1); /* Disable mmap to control data transfer to the audio device */ snd_pcm_plugin_set_disable(data->pcmHandle, PLUGIN_DISABLE_MMAP); /* configure a sound channel */ memset(&data->cparams, 0, sizeof(data->cparams)); data->cparams.mode=SND_PCM_MODE_BLOCK; data->cparams.channel=SND_PCM_CHANNEL_CAPTURE; data->cparams.start_mode=SND_PCM_START_GO; data->cparams.stop_mode=SND_PCM_STOP_STOP; data->cparams.buf.block.frag_size=device->UpdateSize* ChannelsFromDevFmt(device->FmtChans)*BytesFromDevFmt(device->FmtType); data->cparams.buf.block.frags_max=device->NumUpdates; data->cparams.buf.block.frags_min=device->NumUpdates; data->cparams.format.interleave=1; data->cparams.format.rate=device->Frequency; data->cparams.format.voices=ChannelsFromDevFmt(device->FmtChans); data->cparams.format.format=format; if(snd_pcm_plugin_params(data->pcmHandle, &data->cparams) < 0) { snd_pcm_close(data->pcmHandle); free(data); device->ExtraData=NULL; return ALC_INVALID_VALUE; } return ALC_NO_ERROR; }
static ALCenum pa_open_capture(ALCdevice *device, const ALCchar *deviceName) { ALuint frame_size; pa_data *data; PaError err; if(!deviceName) deviceName = pa_device; else if(strcmp(deviceName, pa_device) != 0) return ALC_INVALID_VALUE; data = (pa_data*)calloc(1, sizeof(pa_data)); if(data == NULL) return ALC_OUT_OF_MEMORY; frame_size = FrameSizeFromDevFmt(device->FmtChans, device->FmtType); data->ring = CreateRingBuffer(frame_size, device->UpdateSize*device->NumUpdates); if(data->ring == NULL) goto error; data->params.device = -1; if(!ConfigValueInt(NULL, "port", "capture", &data->params.device) || data->params.device < 0) data->params.device = Pa_GetDefaultInputDevice(); data->params.suggestedLatency = 0.0f; data->params.hostApiSpecificStreamInfo = NULL; switch(device->FmtType) { case DevFmtByte: data->params.sampleFormat = paInt8; break; case DevFmtUByte: data->params.sampleFormat = paUInt8; break; case DevFmtShort: data->params.sampleFormat = paInt16; break; case DevFmtInt: data->params.sampleFormat = paInt32; break; case DevFmtFloat: data->params.sampleFormat = paFloat32; break; case DevFmtUInt: case DevFmtUShort: ERR("%s samples not supported\n", DevFmtTypeString(device->FmtType)); goto error; } data->params.channelCount = ChannelsFromDevFmt(device->FmtChans); err = Pa_OpenStream(&data->stream, &data->params, NULL, device->Frequency, paFramesPerBufferUnspecified, paNoFlag, pa_capture_cb, device); if(err != paNoError) { ERR("Pa_OpenStream() returned an error: %s\n", Pa_GetErrorText(err)); goto error; } al_string_copy_cstr(&device->DeviceName, deviceName); device->ExtraData = data; return ALC_NO_ERROR; error: DestroyRingBuffer(data->ring); free(data); return ALC_INVALID_VALUE; }
static ALCenum pa_open_playback(ALCdevice *device, const ALCchar *deviceName) { pa_data *data; PaError err; if(!deviceName) deviceName = pa_device; else if(strcmp(deviceName, pa_device) != 0) return ALC_INVALID_VALUE; data = (pa_data*)calloc(1, sizeof(pa_data)); data->update_size = device->UpdateSize; data->params.device = -1; if(!ConfigValueInt(NULL, "port", "device", &data->params.device) || data->params.device < 0) data->params.device = Pa_GetDefaultOutputDevice(); data->params.suggestedLatency = (device->UpdateSize*device->NumUpdates) / (float)device->Frequency; data->params.hostApiSpecificStreamInfo = NULL; data->params.channelCount = ((device->FmtChans == DevFmtMono) ? 1 : 2); switch(device->FmtType) { case DevFmtByte: data->params.sampleFormat = paInt8; break; case DevFmtUByte: data->params.sampleFormat = paUInt8; break; case DevFmtUShort: /* fall-through */ case DevFmtShort: data->params.sampleFormat = paInt16; break; case DevFmtUInt: /* fall-through */ case DevFmtInt: data->params.sampleFormat = paInt32; break; case DevFmtFloat: data->params.sampleFormat = paFloat32; break; } retry_open: err = Pa_OpenStream(&data->stream, NULL, &data->params, device->Frequency, device->UpdateSize, paNoFlag, pa_callback, device); if(err != paNoError) { if(data->params.sampleFormat == paFloat32) { data->params.sampleFormat = paInt16; goto retry_open; } ERR("Pa_OpenStream() returned an error: %s\n", Pa_GetErrorText(err)); free(data); return ALC_INVALID_VALUE; } device->ExtraData = data; al_string_copy_cstr(&device->DeviceName, deviceName); return ALC_NO_ERROR; }
int ambdec_load(AmbDecConf *conf, const char *fname) { char *buffer = NULL; size_t maxlen = 0; char *line; FILE *f; f = al_fopen(fname, "r"); if(!f) { ERR("Failed to open: %s\n", fname); return 0; } while((line=read_clipped_line(f, &buffer, &maxlen)) != NULL) { char *saveptr; char *command; command = my_strtok_r(line, "/ \t", &saveptr); if(!command) { ERR("Malformed line: %s\n", line); goto fail; } if(strcmp(command, "description") == 0) { char *value = my_strtok_r(NULL, "", &saveptr); al_string_copy_cstr(&conf->Description, lstrip(value)); } else if(strcmp(command, "version") == 0) { line = my_strtok_r(NULL, "", &saveptr); line = read_uint(&conf->Version, line, 10); if(line && *line != '\0') { ERR("Extra junk after version: %s\n", line); goto fail; } if(conf->Version != 3) { ERR("Unsupported version: %u\n", conf->Version); goto fail; } } else if(strcmp(command, "dec") == 0) { const char *dec = my_strtok_r(NULL, "/ \t", &saveptr); if(strcmp(dec, "chan_mask") == 0) { line = my_strtok_r(NULL, "", &saveptr); line = read_uint(&conf->ChanMask, line, 16); if(line && *line != '\0') { ERR("Extra junk after mask: %s\n", line); goto fail; } } else if(strcmp(dec, "freq_bands") == 0) { line = my_strtok_r(NULL, "", &saveptr); line = read_uint(&conf->FreqBands, line, 10); if(line && *line != '\0') { ERR("Extra junk after freq_bands: %s\n", line); goto fail; } if(conf->FreqBands != 1 && conf->FreqBands != 2) { ERR("Invalid freq_bands value: %u\n", conf->FreqBands); goto fail; } } else if(strcmp(dec, "speakers") == 0) { line = my_strtok_r(NULL, "", &saveptr); line = read_uint(&conf->NumSpeakers, line, 10); if(line && *line != '\0') { ERR("Extra junk after speakers: %s\n", line); goto fail; } if(conf->NumSpeakers > MAX_OUTPUT_CHANNELS) { ERR("Unsupported speaker count: %u\n", conf->NumSpeakers); goto fail; } } else if(strcmp(dec, "coeff_scale") == 0) { line = my_strtok_r(NULL, " \t", &saveptr); if(strcmp(line, "n3d") == 0) conf->CoeffScale = ADS_N3D; else if(strcmp(line, "sn3d") == 0) conf->CoeffScale = ADS_SN3D; else if(strcmp(line, "fuma") == 0) conf->CoeffScale = ADS_FuMa; else { ERR("Unsupported coeff scale: %s\n", line); goto fail; } } else { ERR("Unexpected /dec option: %s\n", dec); goto fail; } } else if(strcmp(command, "opt") == 0) { const char *opt = my_strtok_r(NULL, "/ \t", &saveptr); if(strcmp(opt, "xover_freq") == 0) { line = my_strtok_r(NULL, "", &saveptr); line = read_float(&conf->XOverFreq, line); if(line && *line != '\0') { ERR("Extra junk after xover_freq: %s\n", line); goto fail; } } else if(strcmp(opt, "xover_ratio") == 0) { line = my_strtok_r(NULL, "", &saveptr); line = read_float(&conf->XOverRatio, line); if(line && *line != '\0') { ERR("Extra junk after xover_ratio: %s\n", line); goto fail; } } else if(strcmp(opt, "input_scale") == 0 || strcmp(opt, "nfeff_comp") == 0 || strcmp(opt, "delay_comp") == 0 || strcmp(opt, "level_comp") == 0) { /* Unused */ my_strtok_r(NULL, " \t", &saveptr); } else { ERR("Unexpected /opt option: %s\n", opt); goto fail; } } else if(strcmp(command, "speakers") == 0) { const char *value = my_strtok_r(NULL, "/ \t", &saveptr); if(strcmp(value, "{") != 0) { ERR("Expected { after speakers command, got %s\n", value); goto fail; } if(!load_ambdec_speakers(conf, f, &buffer, &maxlen, &saveptr)) goto fail; value = my_strtok_r(NULL, "/ \t", &saveptr); if(!value) { line = read_clipped_line(f, &buffer, &maxlen); if(!line) { ERR("Unexpected end of file\n"); goto fail; } value = my_strtok_r(line, "/ \t", &saveptr); } if(strcmp(value, "}") != 0) { ERR("Expected } after speaker definitions, got %s\n", value); goto fail; } } else if(strcmp(command, "lfmatrix") == 0 || strcmp(command, "hfmatrix") == 0 || strcmp(command, "matrix") == 0) { const char *value = my_strtok_r(NULL, "/ \t", &saveptr); if(strcmp(value, "{") != 0) { ERR("Expected { after speakers command, got %s\n", value); goto fail; } if(conf->FreqBands == 1) { if(strcmp(command, "matrix") != 0) { ERR("Unexpected \"%s\" type for a single-band decoder\n", command); goto fail; } if(!load_ambdec_matrix(conf->HFOrderGain, conf->HFMatrix, conf->NumSpeakers, f, &buffer, &maxlen, &saveptr)) goto fail; } else { if(strcmp(command, "lfmatrix") == 0) { if(!load_ambdec_matrix(conf->LFOrderGain, conf->LFMatrix, conf->NumSpeakers, f, &buffer, &maxlen, &saveptr)) goto fail; } else if(strcmp(command, "hfmatrix") == 0) { if(!load_ambdec_matrix(conf->HFOrderGain, conf->HFMatrix, conf->NumSpeakers, f, &buffer, &maxlen, &saveptr)) goto fail; } else { ERR("Unexpected \"%s\" type for a dual-band decoder\n", command); goto fail; } } value = my_strtok_r(NULL, "/ \t", &saveptr); if(!value) { line = read_clipped_line(f, &buffer, &maxlen); if(!line) { ERR("Unexpected end of file\n"); goto fail; } value = my_strtok_r(line, "/ \t", &saveptr); } if(strcmp(value, "}") != 0) { ERR("Expected } after matrix definitions, got %s\n", value); goto fail; } } else if(strcmp(command, "end") == 0) { line = my_strtok_r(NULL, "/ \t", &saveptr); if(line) { ERR("Unexpected junk on end: %s\n", line); goto fail; } fclose(f); free(buffer); return 1; } else { ERR("Unexpected command: %s\n", command); goto fail; } line = my_strtok_r(NULL, "/ \t", &saveptr); if(line) { ERR("Unexpected junk on line: %s\n", line); goto fail; } } ERR("Unexpected end of file\n"); fail: fclose(f); free(buffer); return 0; }