Commit 9a5098bb authored by Nikolay Sivov's avatar Nikolay Sivov Committed by Alexandre Julliard

oleaut32: Copy bytes instead of WCHARs in VarBstrCat.

parent 9ad9012f
...@@ -5486,12 +5486,17 @@ static void test_VarBstrCat(void) ...@@ -5486,12 +5486,17 @@ static void test_VarBstrCat(void)
static const WCHAR s1[] = { 'a',0 }; static const WCHAR s1[] = { 'a',0 };
static const WCHAR s2[] = { 'b',0 }; static const WCHAR s2[] = { 'b',0 };
static const WCHAR s1s2[] = { 'a',0,'b',0 }; static const WCHAR s1s2[] = { 'a',0,'b',0 };
static const char str1A[] = "Have ";
static const char str2A[] = "A Cigar";
HRESULT ret; HRESULT ret;
BSTR str1, str2, res; BSTR str1, str2, res;
UINT len;
/* Crash if (0)
{
/* Crash */
ret = VarBstrCat(NULL, NULL, NULL); ret = VarBstrCat(NULL, NULL, NULL);
*/ }
/* Concatenation of two NULL strings works */ /* Concatenation of two NULL strings works */
ret = VarBstrCat(NULL, NULL, &res); ret = VarBstrCat(NULL, NULL, &res);
...@@ -5543,6 +5548,43 @@ static void test_VarBstrCat(void) ...@@ -5543,6 +5548,43 @@ static void test_VarBstrCat(void)
SysFreeString(str2); SysFreeString(str2);
SysFreeString(str1); SysFreeString(str1);
/* Concatenation of ansi BSTRs, both odd byte count not including termination */
str1 = SysAllocStringByteLen(str1A, sizeof(str1A)-1);
str2 = SysAllocStringByteLen(str2A, sizeof(str2A)-1);
len = SysStringLen(str1);
ok(len == (sizeof(str1A)-1)/sizeof(WCHAR), "got length %u\n", len);
len = SysStringLen(str2);
ok(len == (sizeof(str2A)-1)/sizeof(WCHAR), "got length %u\n", len);
ret = VarBstrCat(str1, str2, &res);
ok(ret == S_OK, "VarBstrCat failed: %08x\n", ret);
ok(res != NULL, "Expected a string\n");
len = (sizeof(str1A) + sizeof(str2A) - 2)/sizeof(WCHAR);
ok(SysStringLen(res) == len, "got %d, expected %u\n", SysStringLen(res), len);
ok(!memcmp(res, "Have A Cigar", sizeof(str1A) + sizeof(str2A) - 1), "got (%s)\n", (char*)res);
SysFreeString(res);
SysFreeString(str2);
SysFreeString(str1);
/* Concatenation of ansi BSTRs, both 1 byte length not including termination */
str1 = SysAllocStringByteLen(str1A, 1);
str2 = SysAllocStringByteLen(str2A, 1);
len = SysStringLen(str1);
ok(len == 0, "got length %u\n", len);
len = SysStringLen(str2);
ok(len == 0, "got length %u\n", len);
ret = VarBstrCat(str1, str2, &res);
ok(ret == S_OK, "VarBstrCat failed: %08x\n", ret);
ok(res != NULL, "Expected a string\n");
ok(SysStringLen(res) == 1, "got %d, expected 1\n", SysStringLen(res));
ok(!memcmp(res, "HA", 2), "got (%s)\n", (char*)res);
SysFreeString(res);
SysFreeString(str2);
SysFreeString(str1);
} }
/* IUnknown */ /* IUnknown */
......
...@@ -6932,20 +6932,21 @@ HRESULT WINAPI VarBstrCat(BSTR pbstrLeft, BSTR pbstrRight, BSTR *pbstrOut) ...@@ -6932,20 +6932,21 @@ HRESULT WINAPI VarBstrCat(BSTR pbstrLeft, BSTR pbstrRight, BSTR *pbstrOut)
if (!pbstrOut) if (!pbstrOut)
return E_INVALIDARG; return E_INVALIDARG;
lenLeft = pbstrLeft ? SysStringLen(pbstrLeft) : 0; /* use byte length here to properly handle ansi-allocated BSTRs */
lenRight = pbstrRight ? SysStringLen(pbstrRight) : 0; lenLeft = pbstrLeft ? SysStringByteLen(pbstrLeft) : 0;
lenRight = pbstrRight ? SysStringByteLen(pbstrRight) : 0;
*pbstrOut = SysAllocStringLen(NULL, lenLeft + lenRight); *pbstrOut = SysAllocStringByteLen(NULL, lenLeft + lenRight);
if (!*pbstrOut) if (!*pbstrOut)
return E_OUTOFMEMORY; return E_OUTOFMEMORY;
(*pbstrOut)[0] = '\0'; (*pbstrOut)[0] = '\0';
if (pbstrLeft) if (pbstrLeft)
memcpy(*pbstrOut, pbstrLeft, lenLeft * sizeof(WCHAR)); memcpy(*pbstrOut, pbstrLeft, lenLeft);
if (pbstrRight) if (pbstrRight)
memcpy(*pbstrOut + lenLeft, pbstrRight, lenRight * sizeof(WCHAR)); memcpy((CHAR*)*pbstrOut + lenLeft, pbstrRight, lenRight);
TRACE("%s\n", debugstr_wn(*pbstrOut, SysStringLen(*pbstrOut))); TRACE("%s\n", debugstr_wn(*pbstrOut, SysStringLen(*pbstrOut)));
return S_OK; return S_OK;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment