From b9ce037abb6e1c19389be6e7069d96b32702ba1b Mon Sep 17 00:00:00 2001 From: Nikolay Sivov Date: Fri, 24 Jan 2020 12:21:28 +0300 Subject: [PATCH] ole32: Add support for non-default counter for anti moniker. Signed-off-by: Nikolay Sivov Signed-off-by: Alexandre Julliard --- dlls/ole32/antimoniker.c | 66 +++++++++++++++++++++++--------------- dlls/ole32/tests/moniker.c | 10 ------ 2 files changed, 40 insertions(+), 36 deletions(-) diff --git a/dlls/ole32/antimoniker.c b/dlls/ole32/antimoniker.c index f7912fad789..bff6500fa5f 100644 --- a/dlls/ole32/antimoniker.c +++ b/dlls/ole32/antimoniker.c @@ -40,6 +40,7 @@ typedef struct AntiMonikerImpl{ IROTData IROTData_iface; LONG ref; IUnknown *pMarshal; /* custom marshaler */ + DWORD count; } AntiMonikerImpl; static inline AntiMonikerImpl *impl_from_IMoniker(IMoniker *iface) @@ -168,30 +169,35 @@ AntiMonikerImpl_IsDirty(IMoniker* iface) /****************************************************************************** * AntiMoniker_Load ******************************************************************************/ -static HRESULT WINAPI -AntiMonikerImpl_Load(IMoniker* iface,IStream* pStm) +static HRESULT WINAPI AntiMonikerImpl_Load(IMoniker *iface, IStream *stream) { - DWORD constant=1,dwbuffer; - HRESULT res; + AntiMonikerImpl *moniker = impl_from_IMoniker(iface); + DWORD count = 0; + HRESULT hr; - /* data read by this function is only a DWORD constant (must be 1) ! */ - res=IStream_Read(pStm,&dwbuffer,sizeof(DWORD),NULL); + TRACE("%p, %p.\n", iface, stream); - if (SUCCEEDED(res)&& dwbuffer!=constant) - return E_FAIL; + if (FAILED(hr = IStream_Read(stream, &count, sizeof(count), NULL))) + return hr; - return res; + if (count > 0xfffff) + return E_INVALIDARG; + + moniker->count = count; + + return S_OK; } /****************************************************************************** * AntiMoniker_Save ******************************************************************************/ -static HRESULT WINAPI -AntiMonikerImpl_Save(IMoniker* iface,IStream* pStm,BOOL fClearDirty) +static HRESULT WINAPI AntiMonikerImpl_Save(IMoniker *iface, IStream *stream, BOOL clear_dirty) { - static const DWORD constant = 1; - /* data written by this function is only a DWORD constant set to 1 ! */ - return IStream_Write(pStm,&constant,sizeof(constant),NULL); + AntiMonikerImpl *moniker = impl_from_IMoniker(iface); + + TRACE("%p, %p, %d.\n", iface, stream, clear_dirty); + + return IStream_Write(stream, &moniker->count, sizeof(moniker->count), NULL); } /****************************************************************************** @@ -323,12 +329,16 @@ AntiMonikerImpl_IsEqual(IMoniker* iface,IMoniker* pmkOtherMoniker) /****************************************************************************** * AntiMoniker_Hash ******************************************************************************/ -static HRESULT WINAPI AntiMonikerImpl_Hash(IMoniker* iface,DWORD* pdwHash) +static HRESULT WINAPI AntiMonikerImpl_Hash(IMoniker *iface, DWORD *hash) { - if (pdwHash==NULL) + AntiMonikerImpl *moniker = impl_from_IMoniker(iface); + + TRACE("%p, %p.\n", iface, hash); + + if (!hash) return E_POINTER; - *pdwHash = 0x80000001; + *hash = 0x80000000 | moniker->count; return S_OK; } @@ -434,14 +444,16 @@ AntiMonikerImpl_RelativePathTo(IMoniker* iface,IMoniker* pmOther, IMoniker** ppm * AntiMoniker_GetDisplayName ******************************************************************************/ static HRESULT WINAPI -AntiMonikerImpl_GetDisplayName(IMoniker* iface, IBindCtx* pbc, - IMoniker* pmkToLeft, LPOLESTR *ppszDisplayName) +AntiMonikerImpl_GetDisplayName(IMoniker *iface, IBindCtx *pbc, IMoniker *pmkToLeft, LPOLESTR *displayname) { - static const WCHAR back[]={'\\','.','.',0}; + AntiMonikerImpl *moniker = impl_from_IMoniker(iface); + static const WCHAR nameW[] = {'\\','.','.'}; + WCHAR *ptrW; + int i; - TRACE("(%p,%p,%p,%p)\n",iface,pbc,pmkToLeft,ppszDisplayName); + TRACE("%p, %p, %p, %p.\n", iface, pbc, pmkToLeft, displayname); - if (ppszDisplayName==NULL) + if (!displayname) return E_POINTER; if (pmkToLeft!=NULL){ @@ -449,12 +461,13 @@ AntiMonikerImpl_GetDisplayName(IMoniker* iface, IBindCtx* pbc, return E_NOTIMPL; } - *ppszDisplayName=CoTaskMemAlloc(sizeof(back)); - - if (*ppszDisplayName==NULL) + *displayname = ptrW = CoTaskMemAlloc((moniker->count * ARRAY_SIZE(nameW) + 1) * sizeof(WCHAR)); + if (!*displayname) return E_OUTOFMEMORY; - lstrcpyW(*ppszDisplayName,back); + for (i = 0; i < moniker->count; ++i) + memcpy(ptrW + i * ARRAY_SIZE(nameW), nameW, sizeof(nameW)); + ptrW[moniker->count * ARRAY_SIZE(nameW)] = 0; return S_OK; } @@ -598,6 +611,7 @@ static HRESULT AntiMonikerImpl_Construct(AntiMonikerImpl* This) This->IROTData_iface.lpVtbl = &VT_ROTDataImpl; This->ref = 0; This->pMarshal = NULL; + This->count = 1; return S_OK; } diff --git a/dlls/ole32/tests/moniker.c b/dlls/ole32/tests/moniker.c index e0e30202345..dff6cbbe570 100644 --- a/dlls/ole32/tests/moniker.c +++ b/dlls/ole32/tests/moniker.c @@ -2328,7 +2328,6 @@ todo_wine stream_write_dword(stream, 2); hr = IMoniker_Load(moniker, stream); -todo_wine ok(hr == S_OK, "Unexpected hr %#x.\n", hr); hr = IMoniker_IsEqual(moniker, moniker2); @@ -2341,13 +2340,11 @@ todo_wine hr = IMoniker_Hash(moniker, &hash); ok(hr == S_OK, "Failed to get hash value, hr %#x.\n", hr); -todo_wine ok(hash == 0x80000002, "Unexpected hash value %#x.\n", hash); /* Display name reflects anti combination. */ hr = IMoniker_GetDisplayName(moniker, bindctx, NULL, &name); ok(hr == S_OK, "Failed to get display name, hr %#x.\n", hr); -todo_wine ok(!lstrcmpW(name, L"\\..\\.."), "Unexpected display name %s.\n", wine_dbgstr_w(name)); CoTaskMemFree(name); @@ -2355,30 +2352,25 @@ todo_wine stream_write_dword(stream, 0xfffff); hr = IMoniker_Load(moniker, stream); -todo_wine ok(hr == S_OK, "Unexpected hr %#x.\n", hr); hr = IMoniker_Hash(moniker, &hash); ok(hr == S_OK, "Failed to get hash value, hr %#x.\n", hr); -todo_wine ok(hash == 0x800fffff, "Unexpected hash value %#x.\n", hash); stream_write_dword(stream, 0xfffff + 1); hr = IMoniker_Load(moniker, stream); -todo_wine ok(hr == E_INVALIDARG, "Unexpected hr %#x.\n", hr); hr = IMoniker_Hash(moniker, &hash); ok(hr == S_OK, "Failed to get hash value, hr %#x.\n", hr); -todo_wine ok(hash == 0x800fffff, "Unexpected hash value %#x.\n", hash); /* Zero combining counter is also valid. */ stream_write_dword(stream, 0); hr = IMoniker_Load(moniker, stream); -todo_wine ok(hr == S_OK, "Unexpected hr %#x.\n", hr); hr = IMoniker_IsEqual(moniker, moniker2); @@ -2391,12 +2383,10 @@ todo_wine hr = IMoniker_Hash(moniker, &hash); ok(hr == S_OK, "Failed to get hash value, hr %#x.\n", hr); -todo_wine ok(hash == 0x80000000, "Unexpected hash value %#x.\n", hash); hr = IMoniker_GetDisplayName(moniker, bindctx, NULL, &name); ok(hr == S_OK, "Failed to get display name, hr %#x.\n", hr); -todo_wine ok(!lstrcmpW(name, L""), "Unexpected display name %s.\n", wine_dbgstr_w(name)); CoTaskMemFree(name);