From a6584f5eedd190ce9c6e97540d4e85d1d51c2698 Mon Sep 17 00:00:00 2001 From: Marcus Meissner Date: Mon, 20 Sep 2004 19:11:48 +0000 Subject: [PATCH] SafeArrayGetElement on a VARIANT array does not free the previous VARIANT in the passed pointer. Added testcase. --- dlls/oleaut32/safearray.c | 20 ++++++++++++---- dlls/oleaut32/tests/safearray.c | 42 +++++++++++++++++++++++++++++++++ 2 files changed, 57 insertions(+), 5 deletions(-) diff --git a/dlls/oleaut32/safearray.c b/dlls/oleaut32/safearray.c index 6b61e514f52..0903600e0cb 100644 --- a/dlls/oleaut32/safearray.c +++ b/dlls/oleaut32/safearray.c @@ -342,7 +342,9 @@ static HRESULT SAFEARRAY_DestroyData(SAFEARRAY *psa, ULONG ulStartCell) while(ulCellCount--) { - VariantClear(lpVariant); + HRESULT hRet = VariantClear(lpVariant); + + if (FAILED(hRet)) FIXME("VariantClear of element failed!\n"); lpVariant++; } } @@ -369,7 +371,10 @@ static HRESULT SAFEARRAY_CopyData(SAFEARRAY *psa, SAFEARRAY *dest) while(ulCellCount--) { - VariantCopy(lpDest, lpVariant); + HRESULT hRet; + + hRet = VariantCopy(lpDest, lpVariant); + if (FAILED(hRet)) FIXME("VariantCopy failed with 0x%lx\n", hRet); lpVariant++; lpDest++; } @@ -874,8 +879,10 @@ HRESULT WINAPI SafeArrayPutElement(SAFEARRAY *psa, LONG *rgIndices, void *pvData VARIANT* lpVariant = (VARIANT*)pvData; VARIANT* lpDest = (VARIANT*)lpvDest; - VariantClear(lpDest); - VariantCopy(lpDest, lpVariant); + hRet = VariantClear(lpDest); + if (FAILED(hRet)) FIXME("VariantClear failed with 0x%lx\n", hRet); + hRet = VariantCopy(lpDest, lpVariant); + if (FAILED(hRet)) FIXME("VariantCopy failed with 0x%lx\n", hRet); } else if (psa->fFeatures & FADF_BSTR) { @@ -959,7 +966,10 @@ HRESULT WINAPI SafeArrayGetElement(SAFEARRAY *psa, LONG *rgIndices, void *pvData VARIANT* lpVariant = (VARIANT*)lpvSrc; VARIANT* lpDest = (VARIANT*)pvData; - VariantCopy(lpDest, lpVariant); + /* The original content of pvData is ignored. */ + V_VT(lpDest) = VT_EMPTY; + hRet = VariantCopy(lpDest, lpVariant); + if (FAILED(hRet)) FIXME("VariantCopy failed with 0x%lx\n", hRet); } else if (psa->fFeatures & FADF_BSTR) { diff --git a/dlls/oleaut32/tests/safearray.c b/dlls/oleaut32/tests/safearray.c index 14c1e2bcd43..605a29d7cff 100644 --- a/dlls/oleaut32/tests/safearray.c +++ b/dlls/oleaut32/tests/safearray.c @@ -1087,6 +1087,47 @@ static void test_SafeArrayGetPutElement_IUnknown(void) ok(tunk_xref == 2,"Failed to decrement refcount of iface.\n"); } +static void test_SafeArrayGetPutElement_VARIANT(void) +{ + SAFEARRAYBOUND sab; + LONG indices[1]; + SAFEARRAY *sa; + HRESULT hres; + VARIANT value, gotvalue; + + sab.lLbound = 1; + sab.cElements = 1; + sa = SafeArrayCreate(VT_VARIANT, 1, &sab); + ok(sa != NULL, "VARIANT test couldn't create array\n"); + if (!sa) + return; + + ok(sa->cbElements == sizeof(VARIANT), "VARIANT size mismatch\n"); + if (sa->cbElements != sizeof(VARIANT)) + return; + + indices[0] = sab.lLbound; + V_VT(&value) = VT_I4; + V_I4(&value) = 0x42424242; + hres = SafeArrayPutElement(sa, indices, &value); + ok(hres == S_OK, "Failed to put Variant I4 element hres 0x%lx\n", hres); + + V_VT(&gotvalue) = 0xdead; + hres = SafeArrayGetElement(sa, indices, &gotvalue); + ok(hres == S_OK, "Failed to get variant element at hres 0x%lx\n", hres); + + V_VT(&gotvalue) = VT_EMPTY; + hres = SafeArrayGetElement(sa, indices, &gotvalue); + ok(hres == S_OK, "Failed to get variant element at hres 0x%lx\n", hres); + if (hres == S_OK) { + ok(V_VT(&value) == V_VT(&gotvalue), "Got type 0x%x instead of 0x%x\n", V_VT(&value), V_VT(&gotvalue)); + if (V_VT(&value) == V_VT(&gotvalue)) + ok(V_I4(&value) == V_I4(&gotvalue), "Got %ld instead of %d\n", V_I4(&value), V_VT(&gotvalue)); + } + SafeArrayDestroy(sa); +} + + static void test_SafeArrayCopyData(void) { SAFEARRAYBOUND sab[4]; @@ -1520,4 +1561,5 @@ START_TEST(safearray) test_SafeArrayGetPutElement(); test_SafeArrayGetPutElement_BSTR(); test_SafeArrayGetPutElement_IUnknown(); + test_SafeArrayGetPutElement_VARIANT(); }