ebc7be42e7
- Color management support updated to liblcms version 2. - Various bug fixes.
311 lines
8.8 KiB
C
311 lines
8.8 KiB
C
$NetBSD: patch-dlls_wineoss.drv_mmdevdrv.c,v 1.1 2014/01/17 09:01:58 adam Exp $
|
|
|
|
Restore OSSv3 support for NetBSD.
|
|
|
|
--- dlls/wineoss.drv/mmdevdrv.c.orig 2013-11-15 19:30:24.000000000 +0000
|
|
+++ dlls/wineoss.drv/mmdevdrv.c
|
|
@@ -55,6 +55,10 @@
|
|
|
|
WINE_DEFAULT_DEBUG_CHANNEL(oss);
|
|
|
|
+#ifndef HAVE_OSSv4
|
|
+#define OSS_DEVNODE_SIZE 255
|
|
+#endif
|
|
+
|
|
#define NULL_PTR_ERR MAKE_HRESULT(SEVERITY_ERROR, FACILITY_WIN32, RPC_X_NULL_REF_POINTER)
|
|
|
|
static const REFERENCE_TIME DefaultPeriod = 200000;
|
|
@@ -111,7 +115,9 @@ struct ACImpl {
|
|
float *vols;
|
|
|
|
int fd;
|
|
+#ifdef HAVE_OSSv4
|
|
oss_audioinfo ai;
|
|
+#endif
|
|
char devnode[OSS_DEVNODE_SIZE];
|
|
|
|
BOOL initted, playing;
|
|
@@ -269,7 +275,9 @@ enum DriverPriority {
|
|
int WINAPI AUDDRV_GetPriority(void)
|
|
{
|
|
int mixer_fd;
|
|
+#ifdef HAVE_OSSv4
|
|
oss_sysinfo sysinfo;
|
|
+#endif
|
|
|
|
/* Attempt to determine if we are running on OSS or ALSA's OSS
|
|
* compatibility layer. There is no official way to do that, so just check
|
|
@@ -282,6 +290,7 @@ int WINAPI AUDDRV_GetPriority(void)
|
|
return Priority_Unavailable;
|
|
}
|
|
|
|
+#ifdef HAVE_OSSv4
|
|
sysinfo.version[0] = 0xFF;
|
|
sysinfo.versionnum = ~0;
|
|
if(ioctl(mixer_fd, SNDCTL_SYSINFO, &sysinfo) < 0){
|
|
@@ -289,9 +298,11 @@ int WINAPI AUDDRV_GetPriority(void)
|
|
close(mixer_fd);
|
|
return Priority_Unavailable;
|
|
}
|
|
+#endif
|
|
|
|
close(mixer_fd);
|
|
|
|
+#ifdef HAVE_OSSv4
|
|
if(sysinfo.version[0] < '4' || sysinfo.version[0] > '9'){
|
|
TRACE("Priority_Low: sysinfo.version[0]: %x\n", sysinfo.version[0]);
|
|
return Priority_Low;
|
|
@@ -300,6 +311,7 @@ int WINAPI AUDDRV_GetPriority(void)
|
|
TRACE("Priority_Low: sysinfo.versionnum: %x\n", sysinfo.versionnum);
|
|
return Priority_Low;
|
|
}
|
|
+#endif
|
|
|
|
TRACE("Priority_Preferred: Seems like valid OSS!\n");
|
|
|
|
@@ -406,29 +418,34 @@ static UINT get_default_index(EDataFlow
|
|
{
|
|
int fd = -1, err;
|
|
UINT i;
|
|
+#ifdef HAVE_OSSv4
|
|
oss_audioinfo ai;
|
|
+#endif
|
|
const char *devnode;
|
|
OSSDevice *dev_item;
|
|
|
|
if(flow == eRender)
|
|
- fd = open("/dev/dsp", O_WRONLY | O_NONBLOCK);
|
|
+ fd = open("/dev/audio", O_WRONLY | O_NONBLOCK);
|
|
else
|
|
- fd = open("/dev/dsp", O_RDONLY | O_NONBLOCK);
|
|
+ fd = open("/dev/audio", O_RDONLY | O_NONBLOCK);
|
|
|
|
if(fd < 0){
|
|
WARN("Couldn't open default device!\n");
|
|
return 0;
|
|
}
|
|
|
|
+#ifdef HAVE_OSSv4
|
|
ai.dev = -1;
|
|
if((err = ioctl(fd, SNDCTL_ENGINEINFO, &ai)) < 0){
|
|
WARN("SNDCTL_ENGINEINFO failed: %d (%s)\n", err, strerror(errno));
|
|
close(fd);
|
|
return 0;
|
|
}
|
|
+#endif
|
|
|
|
close(fd);
|
|
|
|
+#ifdef HAVE_OSSv4
|
|
TRACE("Default devnode: %s\n", ai.devnode);
|
|
devnode = oss_clean_devnode(ai.devnode);
|
|
i = 0;
|
|
@@ -439,6 +456,7 @@ static UINT get_default_index(EDataFlow
|
|
++i;
|
|
}
|
|
}
|
|
+#endif
|
|
|
|
WARN("Couldn't find default device! Choosing first.\n");
|
|
return 0;
|
|
@@ -448,7 +466,9 @@ HRESULT WINAPI AUDDRV_GetEndpointIDs(EDa
|
|
UINT *num, UINT *def_index)
|
|
{
|
|
int i, mixer_fd;
|
|
+#ifdef HAVE_OSSv4
|
|
oss_sysinfo sysinfo;
|
|
+#endif
|
|
static int print_once = 0;
|
|
|
|
static const WCHAR outW[] = {'O','u','t',':',' ',0};
|
|
@@ -462,6 +482,7 @@ HRESULT WINAPI AUDDRV_GetEndpointIDs(EDa
|
|
return AUDCLNT_E_SERVICE_NOT_RUNNING;
|
|
}
|
|
|
|
+#ifdef HAVE_OSSv4
|
|
if(ioctl(mixer_fd, SNDCTL_SYSINFO, &sysinfo) < 0){
|
|
close(mixer_fd);
|
|
|
|
@@ -574,6 +595,55 @@ HRESULT WINAPI AUDDRV_GetEndpointIDs(EDa
|
|
}
|
|
}
|
|
|
|
+#else
|
|
+ *ids = HeapAlloc(GetProcessHeap(), 0, sizeof(WCHAR *));
|
|
+ *guids = HeapAlloc(GetProcessHeap(), 0, sizeof(GUID));
|
|
+
|
|
+ *num = 0;
|
|
+ const char *devnode;
|
|
+ OSSDevice *dev_item;
|
|
+ devnode = oss_clean_devnode("/dev/audio");
|
|
+ size_t len, prefix_len;
|
|
+ const WCHAR *prefix;
|
|
+
|
|
+ dev_item = HeapAlloc(GetProcessHeap(), 0, sizeof(*dev_item));
|
|
+
|
|
+ dev_item->flow = flow;
|
|
+ get_device_guid(flow, devnode, &dev_item->guid);
|
|
+ strcpy(dev_item->devnode, devnode);
|
|
+
|
|
+ (*guids)[*num] = dev_item->guid;
|
|
+
|
|
+ len = MultiByteToWideChar(CP_UNIXCP, 0, "OSS AUDIO", -1, NULL, 0);
|
|
+ if(flow == eRender){
|
|
+ prefix = outW;
|
|
+ prefix_len = (sizeof(outW) / sizeof(*outW)) - 1;
|
|
+ len += prefix_len;
|
|
+ }else{
|
|
+ prefix = inW;
|
|
+ prefix_len = (sizeof(inW) / sizeof(*inW)) - 1;
|
|
+ len += prefix_len;
|
|
+ }
|
|
+ (*ids)[*num] = HeapAlloc(GetProcessHeap(), 0,
|
|
+ len * sizeof(WCHAR));
|
|
+ if(!(*ids)[*num]){
|
|
+ for(i = 0; i < *num; ++i)
|
|
+ HeapFree(GetProcessHeap(), 0, (*ids)[i]);
|
|
+ HeapFree(GetProcessHeap(), 0, *ids);
|
|
+ HeapFree(GetProcessHeap(), 0, *guids);
|
|
+ HeapFree(GetProcessHeap(), 0, dev_item);
|
|
+ close(mixer_fd);
|
|
+ return E_OUTOFMEMORY;
|
|
+ }
|
|
+ memcpy((*ids)[*num], prefix, prefix_len * sizeof(WCHAR));
|
|
+ MultiByteToWideChar(CP_UNIXCP, 0, "OSS_AUDIO", -1,
|
|
+ (*ids)[*num] + prefix_len, len - prefix_len);
|
|
+
|
|
+ list_add_tail(&g_devices, &dev_item->entry);
|
|
+
|
|
+ (*num)++;
|
|
+#endif
|
|
+
|
|
close(mixer_fd);
|
|
|
|
*def_index = get_default_index(flow);
|
|
@@ -625,6 +695,7 @@ HRESULT WINAPI AUDDRV_GetAudioEndpoint(G
|
|
|
|
This->dataflow = oss_dev->flow;
|
|
|
|
+#ifdef HAVE_OSSv4
|
|
This->ai.dev = -1;
|
|
if(ioctl(This->fd, SNDCTL_ENGINEINFO, &This->ai) < 0){
|
|
WARN("Unable to get audio info for device %s: %d (%s)\n", oss_dev->devnode,
|
|
@@ -633,9 +704,11 @@ HRESULT WINAPI AUDDRV_GetAudioEndpoint(G
|
|
HeapFree(GetProcessHeap(), 0, This);
|
|
return E_FAIL;
|
|
}
|
|
+#endif
|
|
|
|
strcpy(This->devnode, oss_dev->devnode);
|
|
|
|
+#ifdef HAVE_OSSv4
|
|
TRACE("OSS audioinfo:\n");
|
|
TRACE("devnode: %s\n", This->ai.devnode);
|
|
TRACE("name: %s\n", This->ai.name);
|
|
@@ -648,6 +721,7 @@ HRESULT WINAPI AUDDRV_GetAudioEndpoint(G
|
|
TRACE("max_rate: %d\n", This->ai.max_rate);
|
|
TRACE("min_channels: %d\n", This->ai.min_channels);
|
|
TRACE("max_channels: %d\n", This->ai.max_channels);
|
|
+#endif
|
|
|
|
This->IAudioClient_iface.lpVtbl = &AudioClient_Vtbl;
|
|
This->IAudioRenderClient_iface.lpVtbl = &AudioRenderClient_Vtbl;
|
|
@@ -794,10 +868,12 @@ static int get_oss_format(const WAVEFORM
|
|
return AFMT_U8;
|
|
case 16:
|
|
return AFMT_S16_LE;
|
|
+#ifdef HAVE_OSSv4
|
|
case 24:
|
|
return AFMT_S24_LE;
|
|
case 32:
|
|
return AFMT_S32_LE;
|
|
+#endif
|
|
}
|
|
return -1;
|
|
}
|
|
@@ -1241,10 +1317,14 @@ static HRESULT WINAPI AudioClient_IsForm
|
|
outpwfx = NULL;
|
|
}
|
|
|
|
+#ifndef __NetBSD__
|
|
if(This->dataflow == eRender)
|
|
fd = open(This->devnode, O_WRONLY | O_NONBLOCK, 0);
|
|
else if(This->dataflow == eCapture)
|
|
fd = open(This->devnode, O_RDONLY | O_NONBLOCK, 0);
|
|
+#else
|
|
+ fd = This->fd;
|
|
+#endif
|
|
|
|
if(fd < 0){
|
|
WARN("Unable to open device %s: %d (%s)\n", This->devnode, errno,
|
|
@@ -1254,7 +1334,9 @@ static HRESULT WINAPI AudioClient_IsForm
|
|
|
|
ret = setup_oss_device(mode, fd, pwfx, outpwfx);
|
|
|
|
+#ifndef __NetBSD__
|
|
close(fd);
|
|
+#endif
|
|
|
|
return ret;
|
|
}
|
|
@@ -1272,11 +1354,19 @@ static HRESULT WINAPI AudioClient_GetMix
|
|
return E_POINTER;
|
|
*pwfx = NULL;
|
|
|
|
- if(This->dataflow == eRender)
|
|
+ if(This->dataflow == eRender) {
|
|
+#if HAVE_OSSv4
|
|
formats = This->ai.oformats;
|
|
- else if(This->dataflow == eCapture)
|
|
+#else
|
|
+ formats = AFMT_S16_LE;
|
|
+#endif
|
|
+ } else if(This->dataflow == eCapture) {
|
|
+#if HAVE_OSSv4
|
|
formats = This->ai.iformats;
|
|
- else
|
|
+#else
|
|
+ formats = AFMT_S16_LE;
|
|
+#endif
|
|
+ } else
|
|
return E_UNEXPECTED;
|
|
|
|
fmt = CoTaskMemAlloc(sizeof(WAVEFORMATEXTENSIBLE));
|
|
@@ -1295,12 +1385,14 @@ static HRESULT WINAPI AudioClient_GetMix
|
|
}else if(formats & AFMT_U8){
|
|
fmt->Format.wBitsPerSample = 8;
|
|
fmt->SubFormat = KSDATAFORMAT_SUBTYPE_PCM;
|
|
+#ifdef HAVE_OSSv4
|
|
}else if(formats & AFMT_S32_LE){
|
|
fmt->Format.wBitsPerSample = 32;
|
|
fmt->SubFormat = KSDATAFORMAT_SUBTYPE_PCM;
|
|
}else if(formats & AFMT_S24_LE){
|
|
fmt->Format.wBitsPerSample = 24;
|
|
fmt->SubFormat = KSDATAFORMAT_SUBTYPE_PCM;
|
|
+#endif
|
|
}else{
|
|
WARN("Didn't recognize any available OSS formats: %x\n", formats);
|
|
CoTaskMemFree(fmt);
|
|
@@ -1309,16 +1401,22 @@ static HRESULT WINAPI AudioClient_GetMix
|
|
|
|
/* some OSS drivers are buggy, so set reasonable defaults if
|
|
* the reported values seem wacky */
|
|
+#ifdef HAVE_OSSv4
|
|
fmt->Format.nChannels = max(This->ai.max_channels, This->ai.min_channels);
|
|
if(fmt->Format.nChannels == 0 || fmt->Format.nChannels > 8)
|
|
+#endif
|
|
fmt->Format.nChannels = 2;
|
|
|
|
+#ifdef HAVE_OSSv4
|
|
if(This->ai.max_rate == 0)
|
|
+#endif
|
|
fmt->Format.nSamplesPerSec = 44100;
|
|
+#ifdef HAVE_OSSv4
|
|
else
|
|
fmt->Format.nSamplesPerSec = min(This->ai.max_rate, 44100);
|
|
if(fmt->Format.nSamplesPerSec < This->ai.min_rate)
|
|
fmt->Format.nSamplesPerSec = This->ai.min_rate;
|
|
+#endif
|
|
|
|
fmt->dwChannelMask = get_channel_mask(fmt->Format.nChannels);
|
|
|