summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Alc/alstring.h16
-rw-r--r--Alc/backends/dsound.c119
-rw-r--r--Alc/backends/mmdevapi.c52
-rw-r--r--Alc/helpers.c27
4 files changed, 135 insertions, 79 deletions
diff --git a/Alc/alstring.h b/Alc/alstring.h
index b393a8f4..8f7d1655 100644
--- a/Alc/alstring.h
+++ b/Alc/alstring.h
@@ -1,8 +1,11 @@
#ifndef ALSTRING_H
#define ALSTRING_H
+#include <string.h>
+
#include "vector.h"
+
typedef char al_string_char_type;
DECL_VECTOR(al_string_char_type)
@@ -23,10 +26,23 @@ inline const al_string_char_type *al_string_get_cstr(const_al_string str)
void al_string_clear(al_string *str);
+inline int al_string_cmp(const_al_string str1, const_al_string str2)
+{ return strcmp(al_string_get_cstr(str1), al_string_get_cstr(str2)); }
+
+inline int al_string_cmp_cstr(const_al_string str1, const al_string_char_type *str2)
+{ return strcmp(al_string_get_cstr(str1), str2); }
+
void al_string_copy(al_string *str, const_al_string from);
void al_string_copy_cstr(al_string *str, const al_string_char_type *from);
void al_string_append_char(al_string *str, const al_string_char_type c);
+void al_string_append_cstr(al_string *str, const al_string_char_type *from);
void al_string_append_range(al_string *str, const al_string_char_type *from, const al_string_char_type *to);
+#ifdef _WIN32
+#include <wchar.h>
+/* Windows-only methods to deal with WideChar strings. */
+void al_string_copy_wcstr(al_string *str, const wchar_t *from);
+#endif
+
#endif /* ALSTRING_H */
diff --git a/Alc/backends/dsound.c b/Alc/backends/dsound.c
index 6b108fba..b8fc02d6 100644
--- a/Alc/backends/dsound.c
+++ b/Alc/backends/dsound.c
@@ -36,6 +36,7 @@
#include "alu.h"
#include "threads.h"
#include "compat.h"
+#include "alstring.h"
#ifndef DSSPEAKER_5POINT1
# define DSSPEAKER_5POINT1 0x00000006
@@ -57,14 +58,14 @@ DEFINE_GUID(KSDATAFORMAT_SUBTYPE_IEEE_FLOAT, 0x00000003, 0x0000, 0x0010, 0x80, 0
static void *ds_handle;
static HRESULT (WINAPI *pDirectSoundCreate)(LPCGUID pcGuidDevice, IDirectSound **ppDS, IUnknown *pUnkOuter);
-static HRESULT (WINAPI *pDirectSoundEnumerateA)(LPDSENUMCALLBACKA pDSEnumCallback, void *pContext);
+static HRESULT (WINAPI *pDirectSoundEnumerateW)(LPDSENUMCALLBACKW pDSEnumCallback, void *pContext);
static HRESULT (WINAPI *pDirectSoundCaptureCreate)(LPCGUID pcGuidDevice, IDirectSoundCapture **ppDSC, IUnknown *pUnkOuter);
-static HRESULT (WINAPI *pDirectSoundCaptureEnumerateA)(LPDSENUMCALLBACKA pDSEnumCallback, void *pContext);
+static HRESULT (WINAPI *pDirectSoundCaptureEnumerateW)(LPDSENUMCALLBACKW pDSEnumCallback, void *pContext);
#define DirectSoundCreate pDirectSoundCreate
-#define DirectSoundEnumerateA pDirectSoundEnumerateA
+#define DirectSoundEnumerateW pDirectSoundEnumerateW
#define DirectSoundCaptureCreate pDirectSoundCaptureCreate
-#define DirectSoundCaptureEnumerateA pDirectSoundCaptureEnumerateA
+#define DirectSoundCaptureEnumerateW pDirectSoundCaptureEnumerateW
typedef struct {
@@ -90,7 +91,7 @@ typedef struct {
typedef struct {
- ALCchar *name;
+ al_string name;
GUID guid;
} DevMap;
@@ -121,19 +122,19 @@ static ALCboolean DSoundLoad(void)
} \
} while(0)
LOAD_FUNC(DirectSoundCreate);
- LOAD_FUNC(DirectSoundEnumerateA);
+ LOAD_FUNC(DirectSoundEnumerateW);
LOAD_FUNC(DirectSoundCaptureCreate);
- LOAD_FUNC(DirectSoundCaptureEnumerateA);
+ LOAD_FUNC(DirectSoundCaptureEnumerateW);
#undef LOAD_FUNC
}
return ALC_TRUE;
}
-static BOOL CALLBACK DSoundEnumPlaybackDevices(LPGUID guid, LPCSTR desc, LPCSTR UNUSED(drvname), LPVOID UNUSED(data))
+static BOOL CALLBACK DSoundEnumPlaybackDevices(LPGUID guid, LPCWSTR desc, LPCWSTR UNUSED(drvname), LPVOID UNUSED(data))
{
LPOLESTR guidstr = NULL;
- char str[1024];
+ al_string dname;
HRESULT hr;
void *temp;
int count;
@@ -142,17 +143,22 @@ static BOOL CALLBACK DSoundEnumPlaybackDevices(LPGUID guid, LPCSTR desc, LPCSTR
if(!guid)
return TRUE;
+ AL_STRING_INIT(dname);
+
count = 0;
do {
- if(count == 0)
- snprintf(str, sizeof(str), "%s", desc);
- else
- snprintf(str, sizeof(str), "%s #%d", desc, count+1);
+ al_string_copy_wcstr(&dname, desc);
+ if(count != 0)
+ {
+ char str[64];
+ snprintf(str, sizeof(str), " #%d", count+1);
+ al_string_append_cstr(&dname, str);
+ }
count++;
for(i = 0;i < NumPlaybackDevices;i++)
{
- if(strcmp(str, PlaybackDeviceList[i].name) == 0)
+ if(al_string_cmp(dname, PlaybackDeviceList[i].name) == 0)
break;
}
} while(i != NumPlaybackDevices);
@@ -160,15 +166,17 @@ static BOOL CALLBACK DSoundEnumPlaybackDevices(LPGUID guid, LPCSTR desc, LPCSTR
hr = StringFromCLSID(guid, &guidstr);
if(SUCCEEDED(hr))
{
- TRACE("Got device \"%s\", GUID \"%ls\"\n", str, guidstr);
+ TRACE("Got device \"%s\", GUID \"%ls\"\n", al_string_get_cstr(dname), guidstr);
CoTaskMemFree(guidstr);
}
temp = realloc(PlaybackDeviceList, sizeof(DevMap) * (NumPlaybackDevices+1));
- if(temp)
+ if(!temp)
+ AL_STRING_DEINIT(dname);
+ else
{
PlaybackDeviceList = temp;
- PlaybackDeviceList[NumPlaybackDevices].name = strdup(str);
+ PlaybackDeviceList[NumPlaybackDevices].name = dname;
PlaybackDeviceList[NumPlaybackDevices].guid = *guid;
NumPlaybackDevices++;
}
@@ -177,10 +185,10 @@ static BOOL CALLBACK DSoundEnumPlaybackDevices(LPGUID guid, LPCSTR desc, LPCSTR
}
-static BOOL CALLBACK DSoundEnumCaptureDevices(LPGUID guid, LPCSTR desc, LPCSTR UNUSED(drvname), LPVOID UNUSED(data))
+static BOOL CALLBACK DSoundEnumCaptureDevices(LPGUID guid, LPCWSTR desc, LPCWSTR UNUSED(drvname), LPVOID UNUSED(data))
{
LPOLESTR guidstr = NULL;
- char str[1024];
+ al_string dname;
HRESULT hr;
void *temp;
int count;
@@ -189,17 +197,22 @@ static BOOL CALLBACK DSoundEnumCaptureDevices(LPGUID guid, LPCSTR desc, LPCSTR U
if(!guid)
return TRUE;
+ AL_STRING_INIT(dname);
+
count = 0;
do {
- if(count == 0)
- snprintf(str, sizeof(str), "%s", desc);
- else
- snprintf(str, sizeof(str), "%s #%d", desc, count+1);
+ al_string_copy_wcstr(&dname, desc);
+ if(count != 0)
+ {
+ char str[64];
+ snprintf(str, sizeof(str), " #%d", count+1);
+ al_string_append_cstr(&dname, str);
+ }
count++;
for(i = 0;i < NumCaptureDevices;i++)
{
- if(strcmp(str, CaptureDeviceList[i].name) == 0)
+ if(al_string_cmp(dname, CaptureDeviceList[i].name) == 0)
break;
}
} while(i != NumCaptureDevices);
@@ -207,15 +220,17 @@ static BOOL CALLBACK DSoundEnumCaptureDevices(LPGUID guid, LPCSTR desc, LPCSTR U
hr = StringFromCLSID(guid, &guidstr);
if(SUCCEEDED(hr))
{
- TRACE("Got device \"%s\", GUID \"%ls\"\n", str, guidstr);
+ TRACE("Got device \"%s\", GUID \"%ls\"\n", al_string_get_cstr(dname), guidstr);
CoTaskMemFree(guidstr);
}
temp = realloc(CaptureDeviceList, sizeof(DevMap) * (NumCaptureDevices+1));
- if(temp)
+ if(!temp)
+ AL_STRING_DEINIT(dname);
+ else
{
CaptureDeviceList = temp;
- CaptureDeviceList[NumCaptureDevices].name = strdup(str);
+ CaptureDeviceList[NumCaptureDevices].name = dname;
CaptureDeviceList[NumCaptureDevices].guid = *guid;
NumCaptureDevices++;
}
@@ -336,18 +351,22 @@ static ALCenum DSoundOpenPlayback(ALCdevice *device, const ALCchar *deviceName)
{
DSoundPlaybackData *data = NULL;
LPGUID guid = NULL;
- HRESULT hr;
+ HRESULT hr, hrcom;
if(!PlaybackDeviceList)
{
- hr = DirectSoundEnumerateA(DSoundEnumPlaybackDevices, NULL);
+ /* Initialize COM to prevent name truncation */
+ hrcom = CoInitialize(NULL);
+ hr = DirectSoundEnumerateW(DSoundEnumPlaybackDevices, NULL);
if(FAILED(hr))
- ERR("Error enumerating DirectSound devices (%#x)!\n", (unsigned int)hr);
+ ERR("Error enumerating DirectSound devices (0x%lx)!\n", hr);
+ if(SUCCEEDED(hrcom))
+ CoUninitialize();
}
if(!deviceName && NumPlaybackDevices > 0)
{
- deviceName = PlaybackDeviceList[0].name;
+ deviceName = al_string_get_cstr(PlaybackDeviceList[0].name);
guid = &PlaybackDeviceList[0].guid;
}
else
@@ -356,7 +375,7 @@ static ALCenum DSoundOpenPlayback(ALCdevice *device, const ALCchar *deviceName)
for(i = 0;i < NumPlaybackDevices;i++)
{
- if(strcmp(deviceName, PlaybackDeviceList[i].name) == 0)
+ if(al_string_cmp_cstr(PlaybackDeviceList[i].name, deviceName) == 0)
{
guid = &PlaybackDeviceList[i].guid;
break;
@@ -669,16 +688,16 @@ static ALCenum DSoundOpenCapture(ALCdevice *device, const ALCchar *deviceName)
{
/* Initialize COM to prevent name truncation */
hrcom = CoInitialize(NULL);
- hr = DirectSoundCaptureEnumerateA(DSoundEnumCaptureDevices, NULL);
+ hr = DirectSoundCaptureEnumerateW(DSoundEnumCaptureDevices, NULL);
if(FAILED(hr))
- ERR("Error enumerating DirectSound devices (%#x)!\n", (unsigned int)hr);
+ ERR("Error enumerating DirectSound devices (0x%lx)!\n", hr);
if(SUCCEEDED(hrcom))
CoUninitialize();
}
if(!deviceName && NumCaptureDevices > 0)
{
- deviceName = CaptureDeviceList[0].name;
+ deviceName = al_string_get_cstr(CaptureDeviceList[0].name);
guid = &CaptureDeviceList[0].guid;
}
else
@@ -687,7 +706,7 @@ static ALCenum DSoundOpenCapture(ALCdevice *device, const ALCchar *deviceName)
for(i = 0;i < NumCaptureDevices;i++)
{
- if(strcmp(deviceName, CaptureDeviceList[i].name) == 0)
+ if(al_string_cmp_cstr(CaptureDeviceList[i].name, deviceName) == 0)
{
guid = &CaptureDeviceList[i].guid;
break;
@@ -972,13 +991,13 @@ void alcDSoundDeinit(void)
ALuint i;
for(i = 0;i < NumPlaybackDevices;++i)
- free(PlaybackDeviceList[i].name);
+ AL_STRING_DEINIT(PlaybackDeviceList[i].name);
free(PlaybackDeviceList);
PlaybackDeviceList = NULL;
NumPlaybackDevices = 0;
for(i = 0;i < NumCaptureDevices;++i)
- free(CaptureDeviceList[i].name);
+ AL_STRING_DEINIT(CaptureDeviceList[i].name);
free(CaptureDeviceList);
CaptureDeviceList = NULL;
NumCaptureDevices = 0;
@@ -993,44 +1012,44 @@ void alcDSoundProbe(enum DevProbe type)
HRESULT hr, hrcom;
ALuint i;
+ /* Initialize COM to prevent name truncation */
+ hrcom = CoInitialize(NULL);
switch(type)
{
case ALL_DEVICE_PROBE:
for(i = 0;i < NumPlaybackDevices;++i)
- free(PlaybackDeviceList[i].name);
+ AL_STRING_DEINIT(PlaybackDeviceList[i].name);
free(PlaybackDeviceList);
PlaybackDeviceList = NULL;
NumPlaybackDevices = 0;
- hr = DirectSoundEnumerateA(DSoundEnumPlaybackDevices, NULL);
+ hr = DirectSoundEnumerateW(DSoundEnumPlaybackDevices, NULL);
if(FAILED(hr))
- ERR("Error enumerating DirectSound playback devices (%#x)!\n", (unsigned int)hr);
+ ERR("Error enumerating DirectSound playback devices (0x%lx)!\n", hr);
else
{
for(i = 0;i < NumPlaybackDevices;i++)
- AppendAllDevicesList(PlaybackDeviceList[i].name);
+ AppendAllDevicesList(al_string_get_cstr(PlaybackDeviceList[i].name));
}
break;
case CAPTURE_DEVICE_PROBE:
for(i = 0;i < NumCaptureDevices;++i)
- free(CaptureDeviceList[i].name);
+ AL_STRING_DEINIT(CaptureDeviceList[i].name);
free(CaptureDeviceList);
CaptureDeviceList = NULL;
NumCaptureDevices = 0;
- /* Initialize COM to prevent name truncation */
- hrcom = CoInitialize(NULL);
- hr = DirectSoundCaptureEnumerateA(DSoundEnumCaptureDevices, NULL);
+ hr = DirectSoundCaptureEnumerateW(DSoundEnumCaptureDevices, NULL);
if(FAILED(hr))
- ERR("Error enumerating DirectSound capture devices (%#x)!\n", (unsigned int)hr);
+ ERR("Error enumerating DirectSound capture devices (0x%lx)!\n", hr);
else
{
for(i = 0;i < NumCaptureDevices;i++)
- AppendCaptureDeviceList(CaptureDeviceList[i].name);
+ AppendCaptureDeviceList(al_string_get_cstr(CaptureDeviceList[i].name));
}
- if(SUCCEEDED(hrcom))
- CoUninitialize();
break;
}
+ if(SUCCEEDED(hrcom))
+ CoUninitialize();
}
diff --git a/Alc/backends/mmdevapi.c b/Alc/backends/mmdevapi.c
index bfa283a1..9933c873 100644
--- a/Alc/backends/mmdevapi.c
+++ b/Alc/backends/mmdevapi.c
@@ -42,6 +42,7 @@
#include "alu.h"
#include "threads.h"
#include "compat.h"
+#include "alstring.h"
DEFINE_GUID(KSDATAFORMAT_SUBTYPE_PCM, 0x00000001, 0x0000, 0x0010, 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71);
@@ -76,7 +77,7 @@ typedef struct {
typedef struct {
- ALCchar *name;
+ al_string name;
WCHAR *devid;
} DevMap;
@@ -112,42 +113,29 @@ static HRESULT WaitForResponse(ThreadRequest *req)
}
-static ALCchar *get_device_name(IMMDevice *device)
+static void get_device_name(IMMDevice *device, al_string *name)
{
- ALCchar *name = NULL;
IPropertyStore *ps;
PROPVARIANT pvname;
HRESULT hr;
- int len;
hr = IMMDevice_OpenPropertyStore(device, STGM_READ, &ps);
if(FAILED(hr))
{
WARN("OpenPropertyStore failed: 0x%08lx\n", hr);
- return calloc(1, 1);
+ return;
}
PropVariantInit(&pvname);
hr = IPropertyStore_GetValue(ps, (const PROPERTYKEY*)&DEVPKEY_Device_FriendlyName, &pvname);
if(FAILED(hr))
- {
WARN("GetValue failed: 0x%08lx\n", hr);
- name = calloc(1, 1);
- }
else
- {
- if((len=WideCharToMultiByte(CP_ACP, 0, pvname.pwszVal, -1, NULL, 0, NULL, NULL)) > 0)
- {
- name = calloc(1, len);
- WideCharToMultiByte(CP_ACP, 0, pvname.pwszVal, -1, name, len, NULL, NULL);
- }
- }
+ al_string_copy_wcstr(name, pvname.pwszVal);
PropVariantClear(&pvname);
IPropertyStore_Release(ps);
-
- return name;
}
static void add_device(IMMDevice *device, DevMap *devmap)
@@ -155,12 +143,16 @@ static void add_device(IMMDevice *device, DevMap *devmap)
LPWSTR devid;
HRESULT hr;
+ AL_STRING_INIT(devmap->name);
+
hr = IMMDevice_GetId(device, &devid);
- if(SUCCEEDED(hr))
+ if(FAILED(hr))
+ devmap->devid = calloc(sizeof(WCHAR), 1);
+ else
{
devmap->devid = strdupW(devid);
- devmap->name = get_device_name(device);
- TRACE("Got device \"%s\", \"%ls\"\n", devmap->name, devmap->devid);
+ get_device_name(device, &devmap->name);
+ TRACE("Got device \"%s\", \"%ls\"\n", al_string_get_cstr(devmap->name), devmap->devid);
CoTaskMemFree(devid);
}
}
@@ -660,8 +652,13 @@ static DWORD CALLBACK MMDevApiMsgProc(void *ptr)
hr = IMMDevice_Activate(data->mmdev, &IID_IAudioClient, CLSCTX_INPROC_SERVER, NULL, &ptr);
if(SUCCEEDED(hr))
{
+ al_string str;
+
data->client = ptr;
- device->DeviceName = get_device_name(data->mmdev);
+ AL_STRING_INIT(str);
+ get_device_name(data->mmdev, &str);
+ device->DeviceName = strdup(al_string_get_cstr(str));
+ AL_STRING_DEINIT(str);
}
if(FAILED(hr))
@@ -788,7 +785,7 @@ static DWORD CALLBACK MMDevApiMsgProc(void *ptr)
for(i = 0;i < *numdevs;i++)
{
- free((*devlist)[i].name);
+ AL_STRING_DEINIT((*devlist)[i].name);
free((*devlist)[i].devid);
}
free(*devlist);
@@ -878,7 +875,7 @@ static ALCenum MMDevApiOpenPlayback(ALCdevice *device, const ALCchar *deviceName
hr = E_FAIL;
for(i = 0;i < NumPlaybackDevices;i++)
{
- if(strcmp(deviceName, PlaybackDeviceList[i].name) == 0)
+ if(strcmp(deviceName, al_string_get_cstr(PlaybackDeviceList[i].name)) == 0)
{
data->devid = strdupW(PlaybackDeviceList[i].devid);
hr = S_OK;
@@ -1016,7 +1013,7 @@ void alcMMDevApiDeinit(void)
for(i = 0;i < NumPlaybackDevices;i++)
{
- free(PlaybackDeviceList[i].name);
+ AL_STRING_DEINIT(PlaybackDeviceList[i].name);
free(PlaybackDeviceList[i].devid);
}
free(PlaybackDeviceList);
@@ -1025,7 +1022,7 @@ void alcMMDevApiDeinit(void)
for(i = 0;i < NumCaptureDevices;i++)
{
- free(CaptureDeviceList[i].name);
+ AL_STRING_DEINIT(CaptureDeviceList[i].name);
free(CaptureDeviceList[i].devid);
}
free(CaptureDeviceList);
@@ -1058,10 +1055,7 @@ void alcMMDevApiProbe(enum DevProbe type)
{
ALuint i;
for(i = 0;i < NumPlaybackDevices;i++)
- {
- if(PlaybackDeviceList[i].name)
- AppendAllDevicesList(PlaybackDeviceList[i].name);
- }
+ AppendAllDevicesList(al_string_get_cstr(PlaybackDeviceList[i].name));
}
break;
diff --git a/Alc/helpers.c b/Alc/helpers.c
index 77bfb353..3365f828 100644
--- a/Alc/helpers.c
+++ b/Alc/helpers.c
@@ -794,6 +794,8 @@ ALboolean vector_resize(void *ptr, size_t base_size, size_t obj_count, size_t ob
extern inline ALsizei al_string_length(const_al_string str);
extern inline ALsizei al_string_empty(const_al_string str);
extern inline const al_string_char_type *al_string_get_cstr(const_al_string str);
+extern inline int al_string_cmp(const_al_string str1, const_al_string str2);
+extern inline int al_string_cmp_cstr(const_al_string str1, const al_string_char_type *str2);
void al_string_clear(al_string *str)
{
@@ -831,6 +833,18 @@ void al_string_append_char(al_string *str, const al_string_char_type c)
*VECTOR_ITER_END(*str) = 0;
}
+void al_string_append_cstr(al_string *str, const al_string_char_type *from)
+{
+ size_t len = strlen(from);
+ if(len != 0)
+ {
+ VECTOR_RESERVE(*str, al_string_length(*str)+len+1);
+ VECTOR_RESIZE(*str, al_string_length(*str)+len);
+ memcpy(VECTOR_ITER_END(*str)-len, from, len);
+ *VECTOR_ITER_END(*str) = 0;
+ }
+}
+
void al_string_append_range(al_string *str, const al_string_char_type *from, const al_string_char_type *to)
{
ptrdiff_t len = to - from;
@@ -843,6 +857,19 @@ void al_string_append_range(al_string *str, const al_string_char_type *from, con
}
}
+#ifdef _WIN32
+void al_string_copy_wcstr(al_string *str, const wchar_t *from)
+{
+ int len;
+ if((len=WideCharToMultiByte(CP_UTF8, 0, from, -1, NULL, 0, NULL, NULL)) > 0)
+ {
+ VECTOR_RESERVE(*str, len);
+ VECTOR_RESIZE(*str, len-1);
+ WideCharToMultiByte(CP_UTF8, 0, from, -1, &VECTOR_FRONT(*str), len, NULL, NULL);
+ *VECTOR_ITER_END(*str) = 0;
+ }
+}
+#endif
void InitUIntMap(UIntMap *map, ALsizei limit)