Jacek Caban : ole32: Create interface stub only if it' s not already created.

Alexandre Julliard julliard at wine.codeweavers.com
Mon Aug 31 06:41:59 CDT 2015


Module: wine
Branch: master
Commit: 60451f9855791a6ee4d10ca569153df51249711b
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=60451f9855791a6ee4d10ca569153df51249711b

Author: Jacek Caban <jacek at codeweavers.com>
Date:   Fri Aug 28 14:55:53 2015 +0200

ole32: Create interface stub only if it's not already created.

---

 dlls/ole32/marshal.c | 92 ++++++++++++++++++++++++----------------------------
 1 file changed, 42 insertions(+), 50 deletions(-)

diff --git a/dlls/ole32/marshal.c b/dlls/ole32/marshal.c
index 14f6a5a..9a640c9 100644
--- a/dlls/ole32/marshal.c
+++ b/dlls/ole32/marshal.c
@@ -122,9 +122,7 @@ HRESULT marshal_object(APARTMENT *apt, STDOBJREF *stdobjref, REFIID riid, IUnkno
     struct stub_manager *manager;
     struct ifstub       *ifstub;
     BOOL                 tablemarshal;
-    IRpcStubBuffer      *stub = NULL;
     HRESULT              hr;
-    IUnknown            *iobject = NULL; /* object of type riid */
 
     hr = apartment_getoxid(apt, &stdobjref->oxid);
     if (hr != S_OK)
@@ -134,39 +132,6 @@ HRESULT marshal_object(APARTMENT *apt, STDOBJREF *stdobjref, REFIID riid, IUnkno
     if (hr != S_OK)
         return hr;
 
-    hr = IUnknown_QueryInterface(object, riid, (void **)&iobject);
-    if (hr != S_OK)
-    {
-        ERR("object doesn't expose interface %s, failing with error 0x%08x\n",
-            debugstr_guid(riid), hr);
-        return E_NOINTERFACE;
-    }
-  
-    /* IUnknown doesn't require a stub buffer, because it never goes out on
-     * the wire */
-    if (!IsEqualIID(riid, &IID_IUnknown))
-    {
-        IPSFactoryBuffer *psfb;
-
-        hr = get_facbuf_for_iid(riid, &psfb);
-        if (hr != S_OK)
-        {
-            ERR("couldn't get IPSFactory buffer for interface %s\n", debugstr_guid(riid));
-            IUnknown_Release(iobject);
-            return hr;
-        }
-    
-        hr = IPSFactoryBuffer_CreateStub(psfb, riid, iobject, &stub);
-        IPSFactoryBuffer_Release(psfb);
-        if (hr != S_OK)
-        {
-            ERR("Failed to create an IRpcStubBuffer from IPSFactory for %s with error 0x%08x\n",
-                debugstr_guid(riid), hr);
-            IUnknown_Release(iobject);
-            return hr;
-        }
-    }
-
     stdobjref->flags = SORF_NULL;
     if (mshlflags & MSHLFLAGS_TABLEWEAK)
         stdobjref->flags |= SORFP_TABLEWEAK;
@@ -181,11 +146,7 @@ HRESULT marshal_object(APARTMENT *apt, STDOBJREF *stdobjref, REFIID riid, IUnkno
 
         manager = new_stub_manager(apt, object);
         if (!manager)
-        {
-            if (stub) IRpcStubBuffer_Release(stub);
-            IUnknown_Release(iobject);
             return E_OUTOFMEMORY;
-        }
     }
     stdobjref->oid = manager->oid;
 
@@ -193,19 +154,50 @@ HRESULT marshal_object(APARTMENT *apt, STDOBJREF *stdobjref, REFIID riid, IUnkno
 
     /* make sure ifstub that we are creating is unique */
     ifstub = stub_manager_find_ifstub(manager, riid, mshlflags);
-    if (!ifstub)
-        ifstub = stub_manager_new_ifstub(manager, stub, iobject, riid, dest_context, dest_context_data, mshlflags);
+    if (!ifstub) {
+        IRpcStubBuffer *stub = NULL;
+        IUnknown *iobject = NULL; /* object of type riid */
 
-    if (stub) IRpcStubBuffer_Release(stub);
-    IUnknown_Release(iobject);
+        hr = IUnknown_QueryInterface(object, riid, (void **)&iobject);
+        if (hr != S_OK)
+            ERR("object doesn't expose interface %s, failing with error 0x%08x\n",
+                debugstr_guid(riid), hr);
 
-    if (!ifstub)
-    {
-        stub_manager_int_release(manager);
-        /* destroy the stub manager if it has no ifstubs by releasing
-         * zero external references */
-        stub_manager_ext_release(manager, 0, FALSE, TRUE);
-        return E_OUTOFMEMORY;
+        /* IUnknown doesn't require a stub buffer, because it never goes out on
+         * the wire */
+        if (hr == S_OK && !IsEqualIID(riid, &IID_IUnknown))
+        {
+            IPSFactoryBuffer *psfb;
+
+            hr = get_facbuf_for_iid(riid, &psfb);
+            if (hr == S_OK) {
+                hr = IPSFactoryBuffer_CreateStub(psfb, riid, manager->object, &stub);
+                IPSFactoryBuffer_Release(psfb);
+                if (hr != S_OK)
+                    ERR("Failed to create an IRpcStubBuffer from IPSFactory for %s with error 0x%08x\n",
+                        debugstr_guid(riid), hr);
+            }else {
+                ERR("couldn't get IPSFactory buffer for interface %s\n", debugstr_guid(riid));
+                hr = E_NOINTERFACE;
+            }
+
+        }
+
+        if (hr == S_OK) {
+            ifstub = stub_manager_new_ifstub(manager, stub, iobject, riid, dest_context, dest_context_data, mshlflags);
+            if (!ifstub)
+                hr = E_OUTOFMEMORY;
+        }
+        if (stub) IRpcStubBuffer_Release(stub);
+        if (iobject) IUnknown_Release(iobject);
+
+        if (hr != S_OK) {
+            stub_manager_int_release(manager);
+            /* destroy the stub manager if it has no ifstubs by releasing
+             * zero external references */
+            stub_manager_ext_release(manager, 0, FALSE, TRUE);
+            return hr;
+        }
     }
 
     if (!tablemarshal)




More information about the wine-cvs mailing list