[PATCH] ole32: Partially implement OleCreateStaticFromData() for OLERENDER_FORMAT.

Jactry Zeng jzeng at codeweavers.com
Tue Aug 28 04:25:26 CDT 2018


For bug 42710: https://bugs.winehq.org/show_bug.cgi?id=42710 .

Signed-off-by: Jactry Zeng <jzeng at codeweavers.com>
---
 dlls/ole32/ole2impl.c   | 39 ++++++++++++++++++++++++++--
 dlls/ole32/tests/ole2.c | 57 +++++++++++++++++++++++++++++++++++++++++
 2 files changed, 94 insertions(+), 2 deletions(-)

diff --git a/dlls/ole32/ole2impl.c b/dlls/ole32/ole2impl.c
index fa5777beb0..e2ae3f262e 100644
--- a/dlls/ole32/ole2impl.c
+++ b/dlls/ole32/ole2impl.c
@@ -232,9 +232,44 @@ HRESULT WINAPI OleCreateStaticFromData(IDataObject *data, REFIID iid,
                                        IOleClientSite *client_site, IStorage *stg,
                                        void **obj)
 {
-    FIXME("%p,%s,%08x,%p,%p,%p,%p: semi-stub\n",
+    HRESULT hr;
+
+    TRACE("%p,%s,%08x,%p,%p,%p,%p\n",
           data, debugstr_guid(iid), renderopt, fmt, client_site, stg, obj);
-    return OleCreateFromData(data, iid, renderopt, fmt, client_site, stg, obj);
+
+    if (!obj || !stg)
+        return E_INVALIDARG;
+
+    if (renderopt == OLERENDER_FORMAT)
+    {
+        IOleCache2 *ole_cache = NULL;
+        IPersistStorage *persist = NULL;
+        DWORD connection;
+        STGMEDIUM stgmedium;
+
+        if (!fmt)
+            return E_INVALIDARG;
+
+        if (SUCCEEDED(hr = CreateDataCache(NULL, &CLSID_NULL, &IID_IOleCache2, (LPVOID *)&ole_cache)))
+            if (SUCCEEDED(hr = IOleCache2_Cache(ole_cache, fmt, ADVF_PRIMEFIRST, &connection)))
+                if (SUCCEEDED(hr = IDataObject_GetData(data, fmt, &stgmedium)))
+                    if (SUCCEEDED(hr = IOleCache2_SetData(ole_cache, fmt, &stgmedium, TRUE)))
+                        if (SUCCEEDED(hr = IOleCache2_QueryInterface(ole_cache, &IID_IPersistStorage,
+                                                                     (LPVOID *)&persist)))
+                            if (SUCCEEDED(hr = IPersistStorage_Save(persist, stg, TRUE)))
+                                if (SUCCEEDED(hr = IPersistStorage_SaveCompleted(persist, NULL)))
+                                    hr = OleLoad(stg, iid, client_site, obj);
+        if (persist)
+            IPersistStorage_Release(persist);
+        if (ole_cache)
+            IOleCache2_Release(ole_cache);
+        return hr;
+    }
+    else
+    {
+        FIXME("semi-stub\n");
+        return OleCreateFromData(data, iid, renderopt, fmt, client_site, stg, obj);
+    }
 }
 
 /******************************************************************************
diff --git a/dlls/ole32/tests/ole2.c b/dlls/ole32/tests/ole2.c
index 48c9e0cbab..ceec369dc3 100644
--- a/dlls/ole32/tests/ole2.c
+++ b/dlls/ole32/tests/ole2.c
@@ -4593,6 +4593,62 @@ todo_wine_if(!(test_data[i].in == &stg_def_0 || test_data[i].in == &stg_def_4 ||
     }
 }
 
+static void test_OleCreateStaticFromData(void)
+{
+    HRESULT hr;
+    IOleObject *ole_obj = NULL;
+    IStorage *storage;
+    ILockBytes *ilb;
+    static FORMATETC bitmap_fmt[] =
+    {
+        { CF_BITMAP, NULL, DVASPECT_CONTENT, -1, TYMED_GDI },
+        { 0 }
+    };
+    static const struct expected_method methods_create_from_bitmap[] =
+    {
+        { "DataObject_EnumFormatEtc", TEST_TODO },
+        { "DataObject_GetDataHere", 0 },
+        { "DataObject_QueryGetData", 0, { CF_METAFILEPICT, NULL, DVASPECT_CONTENT, -1, TYMED_ISTORAGE } },
+        { NULL }
+    };
+    static const struct expected_method methods_createstatic_from_bitmap[] =
+    {
+        { "DataObject_GetData", 0, { CF_BITMAP, NULL, DVASPECT_CONTENT, -1, TYMED_GDI } },
+        { NULL }
+    };
+
+    hr = CreateILockBytesOnHGlobal(NULL, TRUE, &ilb);
+    ok(hr == S_OK, "CreateILockBytesOnHGlobal failed: 0x%08x.\n", hr);
+    hr = StgCreateDocfileOnILockBytes(ilb, STGM_SHARE_EXCLUSIVE | STGM_CREATE | STGM_READWRITE,
+                                      0, &storage);
+    ok(hr == S_OK, "StgCreateDocfileOnILockBytes failed: 0x%08x.\n", hr);
+
+    hr = OleCreateStaticFromData(&DataObject, &IID_IOleObject, OLERENDER_FORMAT,
+                                 bitmap_fmt, NULL, NULL, (void **)&ole_obj);
+    ok(hr == E_INVALIDARG, "OleCreateStaticFromData should fail: 0x%08x.\n", hr);
+
+    hr = OleCreateStaticFromData(&DataObject, &IID_IOleObject, OLERENDER_FORMAT,
+                                 bitmap_fmt, NULL, storage, NULL);
+    ok(hr == E_INVALIDARG, "OleCreateStaticFromData should fail: 0x%08x.\n", hr);
+
+    g_dataobject_fmts = bitmap_fmt;
+    expected_method_list = methods_create_from_bitmap;
+    hr = OleCreateFromData(&DataObject, &IID_IOleObject, OLERENDER_FORMAT, bitmap_fmt, NULL,
+                           storage, (void **)&ole_obj);
+    todo_wine ok(hr == DV_E_FORMATETC, "OleCreateFromData should failed: 0x%08x.\n", hr);
+
+    g_dataobject_fmts = bitmap_fmt;
+    expected_method_list = methods_createstatic_from_bitmap;
+    hr = OleCreateStaticFromData(&DataObject, &IID_IOleObject, OLERENDER_FORMAT,
+                                 bitmap_fmt, NULL, storage, (void **)&ole_obj);
+    ok(hr == S_OK, "OleCreateStaticFromData failed: 0x%08x.\n", hr);
+    if (ole_obj)
+        IOleObject_Release(ole_obj);
+
+    IStorage_Release(storage);
+    ILockBytes_Release(ilb);
+}
+
 START_TEST(ole2)
 {
     DWORD dwRegister;
@@ -4643,6 +4699,7 @@ START_TEST(ole2)
     test_data_cache_save();
     test_data_cache_save_data();
     test_data_cache_contents();
+    test_OleCreateStaticFromData();
 
     CoUninitialize();
 }
-- 
2.18.0




More information about the wine-devel mailing list