Commit 63dd8743 authored by Huw Davies's avatar Huw Davies Committed by Alexandre Julliard

ole32: Allow Clone to access the original memory block.

Based on a patch by Dmitry Timoshkov. Signed-off-by: 's avatarHuw Davies <huw@codeweavers.com> Signed-off-by: 's avatarAlexandre Julliard <julliard@winehq.org>
parent f946aa5b
...@@ -51,6 +51,11 @@ struct handle_wrapper ...@@ -51,6 +51,11 @@ struct handle_wrapper
BOOL delete_on_release; BOOL delete_on_release;
}; };
static void handle_addref(struct handle_wrapper *handle)
{
InterlockedIncrement(&handle->ref);
}
static void handle_release(struct handle_wrapper *handle) static void handle_release(struct handle_wrapper *handle)
{ {
ULONG ref = InterlockedDecrement(&handle->ref); ULONG ref = InterlockedDecrement(&handle->ref);
...@@ -586,15 +591,21 @@ static HRESULT WINAPI HGLOBALStreamImpl_Clone( ...@@ -586,15 +591,21 @@ static HRESULT WINAPI HGLOBALStreamImpl_Clone(
IStream* iface, IStream* iface,
IStream** ppstm) /* [out] */ IStream** ppstm) /* [out] */
{ {
HGLOBALStreamImpl* This = impl_from_IStream(iface); HGLOBALStreamImpl* This = impl_from_IStream(iface), *clone;
ULARGE_INTEGER dummy; ULARGE_INTEGER dummy;
LARGE_INTEGER offset; LARGE_INTEGER offset;
HRESULT hr;
TRACE(" Cloning %p (deleteOnRelease=%d seek position=%ld)\n",iface,This->handle->delete_on_release,(long)This->currentPosition.QuadPart); TRACE(" Cloning %p (deleteOnRelease=%d seek position=%ld)\n",iface,This->handle->delete_on_release,(long)This->currentPosition.QuadPart);
hr = CreateStreamOnHGlobal(This->handle->hglobal, FALSE, ppstm);
if(FAILED(hr)) *ppstm = NULL;
return hr;
clone = hglobalstream_construct();
if (!clone) return E_OUTOFMEMORY;
*ppstm = &clone->IStream_iface;
handle_addref(This->handle);
clone->handle = This->handle;
offset.QuadPart = (LONGLONG)This->currentPosition.QuadPart; offset.QuadPart = (LONGLONG)This->currentPosition.QuadPart;
IStream_Seek(*ppstm, offset, STREAM_SEEK_SET, &dummy); IStream_Seek(*ppstm, offset, STREAM_SEEK_SET, &dummy);
return S_OK; return S_OK;
......
...@@ -579,14 +579,12 @@ static void test_IStream_Clone(void) ...@@ -579,14 +579,12 @@ static void test_IStream_Clone(void)
stream_info(clone, &hmem_clone, &size, &pos); stream_info(clone, &hmem_clone, &size, &pos);
ok(hmem_clone == hmem, "handles should match\n"); ok(hmem_clone == hmem, "handles should match\n");
todo_wine
ok(size == 13, "unexpected %d\n", size); ok(size == 13, "unexpected %d\n", size);
ok(pos == 0, "unexpected %d\n", pos); ok(pos == 0, "unexpected %d\n", pos);
buf[0] = 0; buf[0] = 0;
hr = IStream_Read(clone, buf, sizeof(buf), NULL); hr = IStream_Read(clone, buf, sizeof(buf), NULL);
ok(hr == S_OK, "unexpected %#x\n", hr); ok(hr == S_OK, "unexpected %#x\n", hr);
todo_wine
ok(!strcmp(buf, hello), "wrong stream contents\n"); ok(!strcmp(buf, hello), "wrong stream contents\n");
newsize.QuadPart = 0x8000; newsize.QuadPart = 0x8000;
...@@ -600,9 +598,7 @@ todo_wine ...@@ -600,9 +598,7 @@ todo_wine
stream_info(clone, &hmem_clone, &size, &pos); stream_info(clone, &hmem_clone, &size, &pos);
ok(hmem_clone == hmem, "handles should match\n"); ok(hmem_clone == hmem, "handles should match\n");
todo_wine
ok(size == 0x8000, "unexpected %#x\n", size); ok(size == 0x8000, "unexpected %#x\n", size);
todo_wine
ok(pos == 13, "unexpected %d\n", pos); ok(pos == 13, "unexpected %d\n", pos);
IStream_Release(clone); IStream_Release(clone);
...@@ -671,24 +667,19 @@ todo_wine ...@@ -671,24 +667,19 @@ todo_wine
newsize.QuadPart = 0x8000; newsize.QuadPart = 0x8000;
hr = IStream_SetSize(clone, newsize); hr = IStream_SetSize(clone, newsize);
todo_wine
ok(hr == S_OK, "unexpected %#x\n", hr); ok(hr == S_OK, "unexpected %#x\n", hr);
stream_info(clone, &hmem_clone, &size, &pos); stream_info(clone, &hmem_clone, &size, &pos);
ok(hmem_clone == hmem, "handles should match\n"); ok(hmem_clone == hmem, "handles should match\n");
todo_wine
ok(size == 0x8000, "unexpected %#x\n", size); ok(size == 0x8000, "unexpected %#x\n", size);
ok(pos == 0, "unexpected %d\n", pos); ok(pos == 0, "unexpected %d\n", pos);
hr = IStream_Write(clone, hello, sizeof(hello), NULL); hr = IStream_Write(clone, hello, sizeof(hello), NULL);
todo_wine
ok(hr == S_OK, "unexpected %#x\n", hr); ok(hr == S_OK, "unexpected %#x\n", hr);
stream_info(clone, &hmem_clone, &size, &pos); stream_info(clone, &hmem_clone, &size, &pos);
ok(hmem_clone == hmem, "handles should match\n"); ok(hmem_clone == hmem, "handles should match\n");
todo_wine
ok(size == 0x8000, "unexpected %#x\n", size); ok(size == 0x8000, "unexpected %#x\n", size);
todo_wine
ok(pos == 13, "unexpected %d\n", pos); ok(pos == 13, "unexpected %d\n", pos);
offset.QuadPart = 0; offset.QuadPart = 0;
...@@ -698,14 +689,11 @@ todo_wine ...@@ -698,14 +689,11 @@ todo_wine
buf[0] = 0; buf[0] = 0;
hr = IStream_Read(clone, buf, sizeof(buf), NULL); hr = IStream_Read(clone, buf, sizeof(buf), NULL);
ok(hr == S_OK, "unexpected %#x\n", hr); ok(hr == S_OK, "unexpected %#x\n", hr);
todo_wine
ok(!strcmp(buf, hello), "wrong stream contents\n"); ok(!strcmp(buf, hello), "wrong stream contents\n");
stream_info(clone, &hmem_clone, &size, &pos); stream_info(clone, &hmem_clone, &size, &pos);
ok(hmem_clone == hmem, "handles should match\n"); ok(hmem_clone == hmem, "handles should match\n");
todo_wine
ok(size == 0x8000, "unexpected %#x\n", size); ok(size == 0x8000, "unexpected %#x\n", size);
todo_wine
ok(pos == 32, "unexpected %d\n", pos); ok(pos == 32, "unexpected %d\n", pos);
ret = IStream_Release(clone); ret = IStream_Release(clone);
......
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