2 * OLE 2 default object handler
4 * Copyright 1999 Francis Beaudet
5 * Copyright 2000 Abey George
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this library; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
22 * The OLE2 default object handler supports a whole whack of
23 * interfaces including:
24 * IOleObject, IDataObject, IPersistStorage, IViewObject2,
25 * IRunnableObject, IOleCache2, IOleCacheControl and much more.
27 * All the implementation details are taken from: Inside OLE
28 * second edition by Kraig Brockschmidt,
31 * - This implementation of the default handler does not launch the
32 * server in the DoVerb, Update, GetData, GetDataHere and Run
33 * methods. When it is fixed to do so, all the methods will have
34 * to be revisited to allow delegating to the running object
36 * - All methods in the class that use the class ID should be
37 * aware that it is possible for a class to be treated as
38 * another one and go into emulation mode. Nothing has been
41 * - Some functions still return E_NOTIMPL they have to be
42 * implemented. Most of those are related to the running of the
45 * - All the methods related to notification and advise sinks are
46 * in place but no notifications are sent to the sinks yet.
60 #include "compobj_private.h"
62 #include "wine/unicode.h"
63 #include "wine/debug.h"
65 WINE_DEFAULT_DEBUG_CHANNEL(ole);
67 /****************************************************************************
73 const IOleObjectVtbl* lpVtbl;
74 const IUnknownVtbl* lpvtblIUnknown;
75 const IDataObjectVtbl* lpvtblIDataObject;
76 const IRunnableObjectVtbl* lpvtblIRunnableObject;
77 const IAdviseSinkVtbl *lpvtblIAdviseSink;
78 const IPersistStorageVtbl *lpvtblIPersistStorage;
80 /* Reference count of this object */
83 /* IUnknown implementation of the outer object. */
84 IUnknown* outerUnknown;
86 /* Class Id that this handler object represents. */
89 /* IUnknown implementation of the datacache. */
91 /* IPersistStorage implementation of the datacache. */
92 IPersistStorage* dataCache_PersistStg;
94 /* Client site for the embedded object. */
95 IOleClientSite* clientSite;
98 * The IOleAdviseHolder maintains the connections
99 * on behalf of the default handler.
101 IOleAdviseHolder* oleAdviseHolder;
104 * The IDataAdviseHolder maintains the data
105 * connections on behalf of the default handler.
107 IDataAdviseHolder* dataAdviseHolder;
109 /* Name of the container and object contained */
113 /* IOleObject delegate */
114 IOleObject *pOleDelegate;
115 /* IPersistStorage delegate */
116 IPersistStorage *pPSDelegate;
117 /* IDataObject delegate */
118 IDataObject *pDataDelegate;
120 /* connection cookie for the advise on the delegate OLE object */
124 typedef struct DefaultHandler DefaultHandler;
126 static inline DefaultHandler *impl_from_IOleObject( IOleObject *iface )
128 return (DefaultHandler *)((char*)iface - FIELD_OFFSET(DefaultHandler, lpVtbl));
131 static inline DefaultHandler *impl_from_NDIUnknown( IUnknown *iface )
133 return (DefaultHandler *)((char*)iface - FIELD_OFFSET(DefaultHandler, lpvtblIUnknown));
136 static inline DefaultHandler *impl_from_IDataObject( IDataObject *iface )
138 return (DefaultHandler *)((char*)iface - FIELD_OFFSET(DefaultHandler, lpvtblIDataObject));
141 static inline DefaultHandler *impl_from_IRunnableObject( IRunnableObject *iface )
143 return (DefaultHandler *)((char*)iface - FIELD_OFFSET(DefaultHandler, lpvtblIRunnableObject));
146 static inline DefaultHandler *impl_from_IAdviseSink( IAdviseSink *iface )
148 return (DefaultHandler *)((char*)iface - FIELD_OFFSET(DefaultHandler, lpvtblIAdviseSink));
151 static inline DefaultHandler *impl_from_IPersistStorage( IPersistStorage *iface )
153 return (DefaultHandler *)((char*)iface - FIELD_OFFSET(DefaultHandler, lpvtblIPersistStorage));
156 static void DefaultHandler_Destroy(DefaultHandler* This);
158 static inline BOOL object_is_running(DefaultHandler *This)
160 return IRunnableObject_IsRunning((IRunnableObject*)&This->lpvtblIRunnableObject);
163 /*********************************************************
164 * Method implementation for the non delegating IUnknown
165 * part of the DefaultHandler class.
168 /************************************************************************
169 * DefaultHandler_NDIUnknown_QueryInterface (IUnknown)
171 * See Windows documentation for more details on IUnknown methods.
173 * This version of QueryInterface will not delegate its implementation
174 * to the outer unknown.
176 static HRESULT WINAPI DefaultHandler_NDIUnknown_QueryInterface(
181 DefaultHandler *This = impl_from_NDIUnknown(iface);
188 if (IsEqualIID(&IID_IUnknown, riid))
190 else if (IsEqualIID(&IID_IOleObject, riid))
191 *ppvObject = (IOleObject*)&This->lpVtbl;
192 else if (IsEqualIID(&IID_IDataObject, riid))
193 *ppvObject = (IDataObject*)&This->lpvtblIDataObject;
194 else if (IsEqualIID(&IID_IRunnableObject, riid))
195 *ppvObject = (IRunnableObject*)&This->lpvtblIRunnableObject;
196 else if (IsEqualIID(&IID_IPersist, riid) ||
197 IsEqualIID(&IID_IPersistStorage, riid))
198 *ppvObject = &This->lpvtblIPersistStorage;
199 else if (IsEqualIID(&IID_IViewObject, riid) ||
200 IsEqualIID(&IID_IViewObject2, riid) ||
201 IsEqualIID(&IID_IOleCache, riid) ||
202 IsEqualIID(&IID_IOleCache2, riid))
204 HRESULT hr = IUnknown_QueryInterface(This->dataCache, riid, ppvObject);
205 if (FAILED(hr)) FIXME("interface %s not implemented by data cache\n", debugstr_guid(riid));
209 /* Check that we obtained an interface. */
210 if (*ppvObject == NULL)
212 WARN( "() : asking for un supported interface %s\n", debugstr_guid(riid));
213 return E_NOINTERFACE;
217 * Query Interface always increases the reference count by one when it is
220 IUnknown_AddRef((IUnknown*)*ppvObject);
225 /************************************************************************
226 * DefaultHandler_NDIUnknown_AddRef (IUnknown)
228 * See Windows documentation for more details on IUnknown methods.
230 * This version of QueryInterface will not delegate its implementation
231 * to the outer unknown.
233 static ULONG WINAPI DefaultHandler_NDIUnknown_AddRef(
236 DefaultHandler *This = impl_from_NDIUnknown(iface);
237 return InterlockedIncrement(&This->ref);
240 /************************************************************************
241 * DefaultHandler_NDIUnknown_Release (IUnknown)
243 * See Windows documentation for more details on IUnknown methods.
245 * This version of QueryInterface will not delegate its implementation
246 * to the outer unknown.
248 static ULONG WINAPI DefaultHandler_NDIUnknown_Release(
251 DefaultHandler *This = impl_from_NDIUnknown(iface);
254 ref = InterlockedDecrement(&This->ref);
256 if (!ref) DefaultHandler_Destroy(This);
261 /*********************************************************
262 * Methods implementation for the IOleObject part of
263 * the DefaultHandler class.
266 /************************************************************************
267 * DefaultHandler_QueryInterface (IUnknown)
269 * See Windows documentation for more details on IUnknown methods.
271 static HRESULT WINAPI DefaultHandler_QueryInterface(
276 DefaultHandler *This = impl_from_IOleObject(iface);
278 return IUnknown_QueryInterface(This->outerUnknown, riid, ppvObject);
281 /************************************************************************
282 * DefaultHandler_AddRef (IUnknown)
284 * See Windows documentation for more details on IUnknown methods.
286 static ULONG WINAPI DefaultHandler_AddRef(
289 DefaultHandler *This = impl_from_IOleObject(iface);
291 return IUnknown_AddRef(This->outerUnknown);
294 /************************************************************************
295 * DefaultHandler_Release (IUnknown)
297 * See Windows documentation for more details on IUnknown methods.
299 static ULONG WINAPI DefaultHandler_Release(
302 DefaultHandler *This = impl_from_IOleObject(iface);
304 return IUnknown_Release(This->outerUnknown);
307 /************************************************************************
308 * DefaultHandler_SetClientSite (IOleObject)
310 * The default handler's implementation of this method only keeps the
311 * client site pointer for future reference.
313 * See Windows documentation for more details on IOleObject methods.
315 static HRESULT WINAPI DefaultHandler_SetClientSite(
317 IOleClientSite* pClientSite)
319 DefaultHandler *This = impl_from_IOleObject(iface);
322 TRACE("(%p, %p)\n", iface, pClientSite);
324 if (object_is_running(This))
325 hr = IOleObject_SetClientSite(This->pOleDelegate, pClientSite);
328 * Make sure we release the previous client site if there
331 if (This->clientSite)
332 IOleClientSite_Release(This->clientSite);
334 This->clientSite = pClientSite;
336 if (This->clientSite)
337 IOleClientSite_AddRef(This->clientSite);
342 /************************************************************************
343 * DefaultHandler_GetClientSite (IOleObject)
345 * The default handler's implementation of this method returns the
346 * last pointer set in IOleObject_SetClientSite.
348 * See Windows documentation for more details on IOleObject methods.
350 static HRESULT WINAPI DefaultHandler_GetClientSite(
352 IOleClientSite** ppClientSite)
354 DefaultHandler *This = impl_from_IOleObject(iface);
359 *ppClientSite = This->clientSite;
361 if (This->clientSite)
362 IOleClientSite_AddRef(This->clientSite);
367 /************************************************************************
368 * DefaultHandler_SetHostNames (IOleObject)
370 * The default handler's implementation of this method just stores
371 * the strings and returns S_OK.
373 * See Windows documentation for more details on IOleObject methods.
375 static HRESULT WINAPI DefaultHandler_SetHostNames(
377 LPCOLESTR szContainerApp,
378 LPCOLESTR szContainerObj)
380 DefaultHandler *This = impl_from_IOleObject(iface);
382 TRACE("(%p, %s, %s)\n",
384 debugstr_w(szContainerApp),
385 debugstr_w(szContainerObj));
387 if (object_is_running(This))
388 IOleObject_SetHostNames(This->pOleDelegate, szContainerApp, szContainerObj);
390 /* Be sure to cleanup before re-assigning the strings. */
391 HeapFree( GetProcessHeap(), 0, This->containerApp );
392 This->containerApp = NULL;
393 HeapFree( GetProcessHeap(), 0, This->containerObj );
394 This->containerObj = NULL;
398 if ((This->containerApp = HeapAlloc( GetProcessHeap(), 0,
399 (lstrlenW(szContainerApp) + 1) * sizeof(WCHAR) )))
400 strcpyW( This->containerApp, szContainerApp );
405 if ((This->containerObj = HeapAlloc( GetProcessHeap(), 0,
406 (lstrlenW(szContainerObj) + 1) * sizeof(WCHAR) )))
407 strcpyW( This->containerObj, szContainerObj );
412 /* undoes the work done by DefaultHandler_Run */
413 static void DefaultHandler_Stop(DefaultHandler *This)
415 if (!object_is_running(This))
418 IOleObject_Unadvise(This->pOleDelegate, This->dwAdvConn);
420 /* FIXME: call IOleCache_OnStop */
422 if (This->dataAdviseHolder)
423 DataAdviseHolder_OnDisconnect(This->dataAdviseHolder);
424 if (This->pDataDelegate)
426 IDataObject_Release(This->pDataDelegate);
427 This->pDataDelegate = NULL;
429 if (This->pPSDelegate)
431 IPersistStorage_Release(This->pPSDelegate);
432 This->pPSDelegate = NULL;
434 IOleObject_Release(This->pOleDelegate);
435 This->pOleDelegate = NULL;
438 /************************************************************************
439 * DefaultHandler_Close (IOleObject)
441 * The default handler's implementation of this method is meaningless
442 * without a running server so it does nothing.
444 * See Windows documentation for more details on IOleObject methods.
446 static HRESULT WINAPI DefaultHandler_Close(
450 DefaultHandler *This = impl_from_IOleObject(iface);
453 TRACE("(%d)\n", dwSaveOption);
455 if (!object_is_running(This))
458 hr = IOleObject_Close(This->pOleDelegate, dwSaveOption);
460 DefaultHandler_Stop(This);
465 /************************************************************************
466 * DefaultHandler_SetMoniker (IOleObject)
468 * The default handler's implementation of this method does nothing.
470 * See Windows documentation for more details on IOleObject methods.
472 static HRESULT WINAPI DefaultHandler_SetMoniker(
474 DWORD dwWhichMoniker,
477 DefaultHandler *This = impl_from_IOleObject(iface);
479 TRACE("(%p, %d, %p)\n",
484 if (object_is_running(This))
485 return IOleObject_SetMoniker(This->pOleDelegate, dwWhichMoniker, pmk);
490 /************************************************************************
491 * DefaultHandler_GetMoniker (IOleObject)
493 * Delegate this request to the client site if we have one.
495 * See Windows documentation for more details on IOleObject methods.
497 static HRESULT WINAPI DefaultHandler_GetMoniker(
500 DWORD dwWhichMoniker,
503 DefaultHandler *This = impl_from_IOleObject(iface);
505 TRACE("(%p, %d, %d, %p)\n",
506 iface, dwAssign, dwWhichMoniker, ppmk);
508 if (object_is_running(This))
509 return IOleObject_GetMoniker(This->pOleDelegate, dwAssign, dwWhichMoniker,
512 /* FIXME: dwWhichMoniker == OLEWHICHMK_CONTAINER only? */
513 if (This->clientSite)
515 return IOleClientSite_GetMoniker(This->clientSite,
525 /************************************************************************
526 * DefaultHandler_InitFromData (IOleObject)
528 * This method is meaningless if the server is not running
530 * See Windows documentation for more details on IOleObject methods.
532 static HRESULT WINAPI DefaultHandler_InitFromData(
534 IDataObject* pDataObject,
538 DefaultHandler *This = impl_from_IOleObject(iface);
540 TRACE("(%p, %p, %d, %d)\n",
541 iface, pDataObject, fCreation, dwReserved);
543 if (object_is_running(This))
544 return IOleObject_InitFromData(This->pOleDelegate, pDataObject, fCreation,
546 return OLE_E_NOTRUNNING;
549 /************************************************************************
550 * DefaultHandler_GetClipboardData (IOleObject)
552 * This method is meaningless if the server is not running
554 * See Windows documentation for more details on IOleObject methods.
556 static HRESULT WINAPI DefaultHandler_GetClipboardData(
559 IDataObject** ppDataObject)
561 DefaultHandler *This = impl_from_IOleObject(iface);
563 TRACE("(%p, %d, %p)\n",
564 iface, dwReserved, ppDataObject);
566 if (object_is_running(This))
567 return IOleObject_GetClipboardData(This->pOleDelegate, dwReserved,
570 return OLE_E_NOTRUNNING;
573 static HRESULT WINAPI DefaultHandler_DoVerb(
576 struct tagMSG* lpmsg,
577 IOleClientSite* pActiveSite,
582 DefaultHandler *This = impl_from_IOleObject(iface);
583 IRunnableObject *pRunnableObj = (IRunnableObject *)&This->lpvtblIRunnableObject;
586 TRACE("(%d, %p, %p, %d, %p, %s)\n", iVerb, lpmsg, pActiveSite, lindex, hwndParent, wine_dbgstr_rect(lprcPosRect));
588 hr = IRunnableObject_Run(pRunnableObj, NULL);
589 if (FAILED(hr)) return hr;
591 return IOleObject_DoVerb(This->pOleDelegate, iVerb, lpmsg, pActiveSite,
592 lindex, hwndParent, lprcPosRect);
595 /************************************************************************
596 * DefaultHandler_EnumVerbs (IOleObject)
598 * The default handler implementation of this method simply delegates
601 * See Windows documentation for more details on IOleObject methods.
603 static HRESULT WINAPI DefaultHandler_EnumVerbs(
605 IEnumOLEVERB** ppEnumOleVerb)
607 DefaultHandler *This = impl_from_IOleObject(iface);
608 HRESULT hr = OLE_S_USEREG;
610 TRACE("(%p, %p)\n", iface, ppEnumOleVerb);
612 if (object_is_running(This))
613 hr = IOleObject_EnumVerbs(This->pOleDelegate, ppEnumOleVerb);
615 if (hr == OLE_S_USEREG)
616 return OleRegEnumVerbs(&This->clsid, ppEnumOleVerb);
621 static HRESULT WINAPI DefaultHandler_Update(
628 /************************************************************************
629 * DefaultHandler_IsUpToDate (IOleObject)
631 * This method is meaningless if the server is not running
633 * See Windows documentation for more details on IOleObject methods.
635 static HRESULT WINAPI DefaultHandler_IsUpToDate(
638 TRACE("(%p)\n", iface);
640 return OLE_E_NOTRUNNING;
643 /************************************************************************
644 * DefaultHandler_GetUserClassID (IOleObject)
646 * TODO: Map to a new class ID if emulation is active.
648 * See Windows documentation for more details on IOleObject methods.
650 static HRESULT WINAPI DefaultHandler_GetUserClassID(
654 DefaultHandler *This = impl_from_IOleObject(iface);
656 TRACE("(%p, %p)\n", iface, pClsid);
658 if (object_is_running(This))
659 return IOleObject_GetUserClassID(This->pOleDelegate, pClsid);
664 *pClsid = This->clsid;
669 /************************************************************************
670 * DefaultHandler_GetUserType (IOleObject)
672 * The default handler implementation of this method simply delegates
673 * to OleRegGetUserType
675 * See Windows documentation for more details on IOleObject methods.
677 static HRESULT WINAPI DefaultHandler_GetUserType(
680 LPOLESTR* pszUserType)
682 DefaultHandler *This = impl_from_IOleObject(iface);
684 TRACE("(%p, %d, %p)\n", iface, dwFormOfType, pszUserType);
686 return OleRegGetUserType(&This->clsid, dwFormOfType, pszUserType);
689 /************************************************************************
690 * DefaultHandler_SetExtent (IOleObject)
692 * This method is meaningless if the server is not running
694 * See Windows documentation for more details on IOleObject methods.
696 static HRESULT WINAPI DefaultHandler_SetExtent(
701 DefaultHandler *This = impl_from_IOleObject(iface);
703 TRACE("(%p, %x, (%d x %d))\n", iface,
704 dwDrawAspect, psizel->cx, psizel->cy);
706 if (object_is_running(This))
707 return IOleObject_SetExtent(This->pOleDelegate, dwDrawAspect, psizel);
709 return OLE_E_NOTRUNNING;
712 /************************************************************************
713 * DefaultHandler_GetExtent (IOleObject)
715 * The default handler's implementation of this method returns uses
716 * the cache to locate the aspect and extract the extent from it.
718 * See Windows documentation for more details on IOleObject methods.
720 static HRESULT WINAPI DefaultHandler_GetExtent(
725 DVTARGETDEVICE* targetDevice;
726 IViewObject2* cacheView = NULL;
729 DefaultHandler *This = impl_from_IOleObject(iface);
731 TRACE("(%p, %x, %p)\n", iface, dwDrawAspect, psizel);
733 if (object_is_running(This))
734 return IOleObject_GetExtent(This->pOleDelegate, dwDrawAspect, psizel);
736 hres = IUnknown_QueryInterface(This->dataCache, &IID_IViewObject2, (void**)&cacheView);
741 * Prepare the call to the cache's GetExtent method.
743 * Here we would build a valid DVTARGETDEVICE structure
744 * but, since we are calling into the data cache, we
745 * know its implementation and we'll skip this
746 * extra work until later.
750 hres = IViewObject2_GetExtent(cacheView,
756 IViewObject2_Release(cacheView);
761 /************************************************************************
762 * DefaultHandler_Advise (IOleObject)
764 * The default handler's implementation of this method simply
765 * delegates to the OleAdviseHolder.
767 * See Windows documentation for more details on IOleObject methods.
769 static HRESULT WINAPI DefaultHandler_Advise(
771 IAdviseSink* pAdvSink,
772 DWORD* pdwConnection)
775 DefaultHandler *This = impl_from_IOleObject(iface);
777 TRACE("(%p, %p, %p)\n", iface, pAdvSink, pdwConnection);
779 /* Make sure we have an advise holder before we start. */
780 if (!This->oleAdviseHolder)
781 hres = CreateOleAdviseHolder(&This->oleAdviseHolder);
784 hres = IOleAdviseHolder_Advise(This->oleAdviseHolder,
791 /************************************************************************
792 * DefaultHandler_Unadvise (IOleObject)
794 * The default handler's implementation of this method simply
795 * delegates to the OleAdviseHolder.
797 * See Windows documentation for more details on IOleObject methods.
799 static HRESULT WINAPI DefaultHandler_Unadvise(
803 DefaultHandler *This = impl_from_IOleObject(iface);
805 TRACE("(%p, %d)\n", iface, dwConnection);
808 * If we don't have an advise holder yet, it means we don't have
811 if (!This->oleAdviseHolder)
812 return OLE_E_NOCONNECTION;
814 return IOleAdviseHolder_Unadvise(This->oleAdviseHolder,
818 /************************************************************************
819 * DefaultHandler_EnumAdvise (IOleObject)
821 * The default handler's implementation of this method simply
822 * delegates to the OleAdviseHolder.
824 * See Windows documentation for more details on IOleObject methods.
826 static HRESULT WINAPI DefaultHandler_EnumAdvise(
828 IEnumSTATDATA** ppenumAdvise)
830 DefaultHandler *This = impl_from_IOleObject(iface);
832 TRACE("(%p, %p)\n", iface, ppenumAdvise);
837 *ppenumAdvise = NULL;
839 if (!This->oleAdviseHolder)
842 return IOleAdviseHolder_EnumAdvise(This->oleAdviseHolder, ppenumAdvise);
845 /************************************************************************
846 * DefaultHandler_GetMiscStatus (IOleObject)
848 * The default handler's implementation of this method simply delegates
849 * to OleRegGetMiscStatus.
851 * See Windows documentation for more details on IOleObject methods.
853 static HRESULT WINAPI DefaultHandler_GetMiscStatus(
859 DefaultHandler *This = impl_from_IOleObject(iface);
861 TRACE("(%p, %x, %p)\n", iface, dwAspect, pdwStatus);
863 if (object_is_running(This))
864 return IOleObject_GetMiscStatus(This->pOleDelegate, dwAspect, pdwStatus);
866 hres = OleRegGetMiscStatus(&This->clsid, dwAspect, pdwStatus);
874 /************************************************************************
875 * DefaultHandler_SetColorScheme (IOleObject)
877 * This method is meaningless if the server is not running
879 * See Windows documentation for more details on IOleObject methods.
881 static HRESULT WINAPI DefaultHandler_SetColorScheme(
883 struct tagLOGPALETTE* pLogpal)
885 DefaultHandler *This = impl_from_IOleObject(iface);
887 TRACE("(%p, %p))\n", iface, pLogpal);
889 if (object_is_running(This))
890 return IOleObject_SetColorScheme(This->pOleDelegate, pLogpal);
892 return OLE_E_NOTRUNNING;
895 /*********************************************************
896 * Methods implementation for the IDataObject part of
897 * the DefaultHandler class.
900 /************************************************************************
901 * DefaultHandler_IDataObject_QueryInterface (IUnknown)
903 * See Windows documentation for more details on IUnknown methods.
905 static HRESULT WINAPI DefaultHandler_IDataObject_QueryInterface(
910 DefaultHandler *This = impl_from_IDataObject(iface);
912 return IUnknown_QueryInterface(This->outerUnknown, riid, ppvObject);
915 /************************************************************************
916 * DefaultHandler_IDataObject_AddRef (IUnknown)
918 * See Windows documentation for more details on IUnknown methods.
920 static ULONG WINAPI DefaultHandler_IDataObject_AddRef(
923 DefaultHandler *This = impl_from_IDataObject(iface);
925 return IUnknown_AddRef(This->outerUnknown);
928 /************************************************************************
929 * DefaultHandler_IDataObject_Release (IUnknown)
931 * See Windows documentation for more details on IUnknown methods.
933 static ULONG WINAPI DefaultHandler_IDataObject_Release(
936 DefaultHandler *This = impl_from_IDataObject(iface);
938 return IUnknown_Release(This->outerUnknown);
941 /************************************************************************
942 * DefaultHandler_GetData
944 * Get Data from a source dataobject using format pformatetcIn->cfFormat
945 * See Windows documentation for more details on GetData.
946 * Default handler's implementation of this method delegates to the cache.
948 static HRESULT WINAPI DefaultHandler_GetData(
950 LPFORMATETC pformatetcIn,
953 IDataObject* cacheDataObject = NULL;
956 DefaultHandler *This = impl_from_IDataObject(iface);
958 TRACE("(%p, %p, %p)\n", iface, pformatetcIn, pmedium);
960 hres = IUnknown_QueryInterface(This->dataCache,
962 (void**)&cacheDataObject);
967 hres = IDataObject_GetData(cacheDataObject,
971 IDataObject_Release(cacheDataObject);
973 if (FAILED(hres) && This->pDataDelegate)
974 hres = IDataObject_GetData(This->pDataDelegate, pformatetcIn, pmedium);
979 static HRESULT WINAPI DefaultHandler_GetDataHere(
981 LPFORMATETC pformatetc,
988 /************************************************************************
989 * DefaultHandler_QueryGetData (IDataObject)
991 * The default handler's implementation of this method delegates to
994 * See Windows documentation for more details on IDataObject methods.
996 static HRESULT WINAPI DefaultHandler_QueryGetData(
998 LPFORMATETC pformatetc)
1000 IDataObject* cacheDataObject = NULL;
1003 DefaultHandler *This = impl_from_IDataObject(iface);
1005 TRACE("(%p, %p)\n", iface, pformatetc);
1007 hres = IUnknown_QueryInterface(This->dataCache,
1009 (void**)&cacheDataObject);
1012 return E_UNEXPECTED;
1014 hres = IDataObject_QueryGetData(cacheDataObject,
1017 IDataObject_Release(cacheDataObject);
1019 if (FAILED(hres) && This->pDataDelegate)
1020 hres = IDataObject_QueryGetData(This->pDataDelegate, pformatetc);
1025 /************************************************************************
1026 * DefaultHandler_GetCanonicalFormatEtc (IDataObject)
1028 * This method is meaningless if the server is not running
1030 * See Windows documentation for more details on IDataObject methods.
1032 static HRESULT WINAPI DefaultHandler_GetCanonicalFormatEtc(
1034 LPFORMATETC pformatetcIn,
1035 LPFORMATETC pformatetcOut)
1037 DefaultHandler *This = impl_from_IDataObject(iface);
1039 TRACE("(%p, %p, %p)\n", iface, pformatetcIn, pformatetcOut);
1041 if (!This->pDataDelegate)
1042 return OLE_E_NOTRUNNING;
1044 return IDataObject_GetCanonicalFormatEtc(This->pDataDelegate, pformatetcIn, pformatetcOut);
1047 /************************************************************************
1048 * DefaultHandler_SetData (IDataObject)
1050 * The default handler's implementation of this method delegates to
1053 * See Windows documentation for more details on IDataObject methods.
1055 static HRESULT WINAPI DefaultHandler_SetData(
1057 LPFORMATETC pformatetc,
1061 DefaultHandler *This = impl_from_IDataObject(iface);
1062 IDataObject* cacheDataObject = NULL;
1065 TRACE("(%p, %p, %p, %d)\n", iface, pformatetc, pmedium, fRelease);
1067 hres = IUnknown_QueryInterface(This->dataCache,
1069 (void**)&cacheDataObject);
1072 return E_UNEXPECTED;
1074 hres = IDataObject_SetData(cacheDataObject,
1079 IDataObject_Release(cacheDataObject);
1084 /************************************************************************
1085 * DefaultHandler_EnumFormatEtc (IDataObject)
1087 * The default handler's implementation of This method simply delegates
1088 * to OleRegEnumFormatEtc.
1090 * See Windows documentation for more details on IDataObject methods.
1092 static HRESULT WINAPI DefaultHandler_EnumFormatEtc(
1095 IEnumFORMATETC** ppenumFormatEtc)
1098 DefaultHandler *This = impl_from_IDataObject(iface);
1100 TRACE("(%p, %x, %p)\n", iface, dwDirection, ppenumFormatEtc);
1102 hres = OleRegEnumFormatEtc(&This->clsid, dwDirection, ppenumFormatEtc);
1107 /************************************************************************
1108 * DefaultHandler_DAdvise (IDataObject)
1110 * The default handler's implementation of this method simply
1111 * delegates to the DataAdviseHolder.
1113 * See Windows documentation for more details on IDataObject methods.
1115 static HRESULT WINAPI DefaultHandler_DAdvise(
1117 FORMATETC* pformatetc,
1119 IAdviseSink* pAdvSink,
1120 DWORD* pdwConnection)
1122 HRESULT hres = S_OK;
1123 DefaultHandler *This = impl_from_IDataObject(iface);
1125 TRACE("(%p, %p, %d, %p, %p)\n",
1126 iface, pformatetc, advf, pAdvSink, pdwConnection);
1128 /* Make sure we have a data advise holder before we start. */
1129 if (!This->dataAdviseHolder)
1131 hres = CreateDataAdviseHolder(&This->dataAdviseHolder);
1132 if (SUCCEEDED(hres) && This->pDataDelegate)
1133 DataAdviseHolder_OnConnect(This->dataAdviseHolder, This->pDataDelegate);
1136 if (SUCCEEDED(hres))
1137 hres = IDataAdviseHolder_Advise(This->dataAdviseHolder,
1147 /************************************************************************
1148 * DefaultHandler_DUnadvise (IDataObject)
1150 * The default handler's implementation of this method simply
1151 * delegates to the DataAdviseHolder.
1153 * See Windows documentation for more details on IDataObject methods.
1155 static HRESULT WINAPI DefaultHandler_DUnadvise(
1159 DefaultHandler *This = impl_from_IDataObject(iface);
1161 TRACE("(%p, %d)\n", iface, dwConnection);
1164 * If we don't have a data advise holder yet, it means that
1165 * we don't have any connections..
1167 if (!This->dataAdviseHolder)
1168 return OLE_E_NOCONNECTION;
1170 return IDataAdviseHolder_Unadvise(This->dataAdviseHolder,
1174 /************************************************************************
1175 * DefaultHandler_EnumDAdvise (IDataObject)
1177 * The default handler's implementation of this method simply
1178 * delegates to the DataAdviseHolder.
1180 * See Windows documentation for more details on IDataObject methods.
1182 static HRESULT WINAPI DefaultHandler_EnumDAdvise(
1184 IEnumSTATDATA** ppenumAdvise)
1186 DefaultHandler *This = impl_from_IDataObject(iface);
1188 TRACE("(%p, %p)\n", iface, ppenumAdvise);
1193 *ppenumAdvise = NULL;
1195 /* If we have a data advise holder object, delegate. */
1196 if (This->dataAdviseHolder)
1197 return IDataAdviseHolder_EnumAdvise(This->dataAdviseHolder,
1203 /*********************************************************
1204 * Methods implementation for the IRunnableObject part
1205 * of the DefaultHandler class.
1208 /************************************************************************
1209 * DefaultHandler_IRunnableObject_QueryInterface (IUnknown)
1211 * See Windows documentation for more details on IUnknown methods.
1213 static HRESULT WINAPI DefaultHandler_IRunnableObject_QueryInterface(
1214 IRunnableObject* iface,
1218 DefaultHandler *This = impl_from_IRunnableObject(iface);
1220 return IUnknown_QueryInterface(This->outerUnknown, riid, ppvObject);
1223 /************************************************************************
1224 * DefaultHandler_IRunnableObject_AddRef (IUnknown)
1226 * See Windows documentation for more details on IUnknown methods.
1228 static ULONG WINAPI DefaultHandler_IRunnableObject_AddRef(
1229 IRunnableObject* iface)
1231 DefaultHandler *This = impl_from_IRunnableObject(iface);
1233 return IUnknown_AddRef(This->outerUnknown);
1236 /************************************************************************
1237 * DefaultHandler_IRunnableObject_Release (IUnknown)
1239 * See Windows documentation for more details on IUnknown methods.
1241 static ULONG WINAPI DefaultHandler_IRunnableObject_Release(
1242 IRunnableObject* iface)
1244 DefaultHandler *This = impl_from_IRunnableObject(iface);
1246 return IUnknown_Release(This->outerUnknown);
1249 /************************************************************************
1250 * DefaultHandler_GetRunningClass (IRunnableObject)
1252 * See Windows documentation for more details on IRunnableObject methods.
1254 static HRESULT WINAPI DefaultHandler_GetRunningClass(
1255 IRunnableObject* iface,
1262 static HRESULT WINAPI DefaultHandler_Run(
1263 IRunnableObject* iface,
1266 DefaultHandler *This = impl_from_IRunnableObject(iface);
1269 FIXME("(%p): semi-stub\n", pbc);
1271 /* already running? if so nothing to do */
1272 if (object_is_running(This))
1275 hr = CoCreateInstance(&This->clsid, NULL, CLSCTX_LOCAL_SERVER,
1276 &IID_IOleObject, (void **)&This->pOleDelegate);
1280 hr = IOleObject_Advise(This->pOleDelegate,
1281 (IAdviseSink *)&This->lpvtblIAdviseSink,
1284 if (SUCCEEDED(hr) && This->clientSite)
1285 hr = IOleObject_SetClientSite(This->pOleDelegate, This->clientSite);
1289 IOleObject_QueryInterface(This->pOleDelegate, &IID_IPersistStorage,
1290 (void **)&This->pPSDelegate);
1291 if (This->pPSDelegate)
1292 hr = IPersistStorage_InitNew(This->pPSDelegate, NULL);
1295 if (SUCCEEDED(hr) && This->containerApp)
1296 hr = IOleObject_SetHostNames(This->pOleDelegate, This->containerApp,
1297 This->containerObj);
1299 /* FIXME: do more stuff here:
1300 * - IOleObject_GetMiscStatus
1301 * - IOleObject_GetMoniker
1306 hr = IOleObject_QueryInterface(This->pOleDelegate, &IID_IDataObject,
1307 (void **)&This->pDataDelegate);
1309 if (SUCCEEDED(hr) && This->dataAdviseHolder)
1310 hr = DataAdviseHolder_OnConnect(This->dataAdviseHolder, This->pDataDelegate);
1313 DefaultHandler_Stop(This);
1318 /************************************************************************
1319 * DefaultHandler_IsRunning (IRunnableObject)
1321 * See Windows documentation for more details on IRunnableObject methods.
1323 static BOOL WINAPI DefaultHandler_IsRunning(
1324 IRunnableObject* iface)
1326 DefaultHandler *This = impl_from_IRunnableObject(iface);
1330 if (This->pOleDelegate)
1336 /************************************************************************
1337 * DefaultHandler_LockRunning (IRunnableObject)
1339 * See Windows documentation for more details on IRunnableObject methods.
1341 static HRESULT WINAPI DefaultHandler_LockRunning(
1342 IRunnableObject* iface,
1344 BOOL fLastUnlockCloses)
1350 /************************************************************************
1351 * DefaultHandler_SetContainedObject (IRunnableObject)
1353 * See Windows documentation for more details on IRunnableObject methods.
1355 static HRESULT WINAPI DefaultHandler_SetContainedObject(
1356 IRunnableObject* iface,
1363 static HRESULT WINAPI DefaultHandler_IAdviseSink_QueryInterface(
1368 if (IsEqualIID(riid, &IID_IUnknown) ||
1369 IsEqualIID(riid, &IID_IAdviseSink))
1372 IAdviseSink_AddRef(iface);
1376 return E_NOINTERFACE;
1379 static ULONG WINAPI DefaultHandler_IAdviseSink_AddRef(
1382 DefaultHandler *This = impl_from_IAdviseSink(iface);
1384 return IUnknown_AddRef((IUnknown *)&This->lpvtblIUnknown);
1387 static ULONG WINAPI DefaultHandler_IAdviseSink_Release(
1390 DefaultHandler *This = impl_from_IAdviseSink(iface);
1392 return IUnknown_Release((IUnknown *)&This->lpvtblIUnknown);
1395 static void WINAPI DefaultHandler_IAdviseSink_OnDataChange(
1397 FORMATETC *pFormatetc,
1403 static void WINAPI DefaultHandler_IAdviseSink_OnViewChange(
1411 static void WINAPI DefaultHandler_IAdviseSink_OnRename(
1415 DefaultHandler *This = impl_from_IAdviseSink(iface);
1417 TRACE("(%p)\n", pmk);
1419 if (This->oleAdviseHolder)
1420 IOleAdviseHolder_SendOnRename(This->oleAdviseHolder, pmk);
1423 static void WINAPI DefaultHandler_IAdviseSink_OnSave(
1426 DefaultHandler *This = impl_from_IAdviseSink(iface);
1430 if (This->oleAdviseHolder)
1431 IOleAdviseHolder_SendOnSave(This->oleAdviseHolder);
1434 static void WINAPI DefaultHandler_IAdviseSink_OnClose(
1437 DefaultHandler *This = impl_from_IAdviseSink(iface);
1441 if (This->oleAdviseHolder)
1442 IOleAdviseHolder_SendOnClose(This->oleAdviseHolder);
1444 DefaultHandler_Stop(This);
1448 /************************************************************************
1449 * DefaultHandler_IPersistStorage_QueryInterface
1452 static HRESULT WINAPI DefaultHandler_IPersistStorage_QueryInterface(
1453 IPersistStorage* iface,
1457 DefaultHandler *This = impl_from_IPersistStorage(iface);
1459 return IUnknown_QueryInterface(This->outerUnknown, riid, ppvObject);
1462 /************************************************************************
1463 * DefaultHandler_IPersistStorage_AddRef
1466 static ULONG WINAPI DefaultHandler_IPersistStorage_AddRef(
1467 IPersistStorage* iface)
1469 DefaultHandler *This = impl_from_IPersistStorage(iface);
1471 return IUnknown_AddRef(This->outerUnknown);
1474 /************************************************************************
1475 * DefaultHandler_IPersistStorage_Release
1478 static ULONG WINAPI DefaultHandler_IPersistStorage_Release(
1479 IPersistStorage* iface)
1481 DefaultHandler *This = impl_from_IPersistStorage(iface);
1483 return IUnknown_Release(This->outerUnknown);
1486 /************************************************************************
1487 * DefaultHandler_IPersistStorage_GetClassID
1490 static HRESULT WINAPI DefaultHandler_IPersistStorage_GetClassID(
1491 IPersistStorage* iface,
1494 DefaultHandler *This = impl_from_IPersistStorage(iface);
1496 return IPersistStorage_GetClassID(This->dataCache_PersistStg, clsid);
1499 /************************************************************************
1500 * DefaultHandler_IPersistStorage_IsDirty
1503 static HRESULT WINAPI DefaultHandler_IPersistStorage_IsDirty(
1504 IPersistStorage* iface)
1506 DefaultHandler *This = impl_from_IPersistStorage(iface);
1508 return IPersistStorage_IsDirty(This->dataCache_PersistStg);
1511 /************************************************************************
1512 * DefaultHandler_IPersistStorage_InitNew
1515 static HRESULT WINAPI DefaultHandler_IPersistStorage_InitNew(
1516 IPersistStorage* iface,
1519 DefaultHandler *This = impl_from_IPersistStorage(iface);
1521 return IPersistStorage_InitNew(This->dataCache_PersistStg, pStg);
1525 /************************************************************************
1526 * DefaultHandler_IPersistStorage_Load
1529 static HRESULT WINAPI DefaultHandler_IPersistStorage_Load(
1530 IPersistStorage* iface,
1533 DefaultHandler *This = impl_from_IPersistStorage(iface);
1535 return IPersistStorage_Load(This->dataCache_PersistStg, pStg);
1539 /************************************************************************
1540 * DefaultHandler_IPersistStorage_Save
1543 static HRESULT WINAPI DefaultHandler_IPersistStorage_Save(
1544 IPersistStorage* iface,
1548 DefaultHandler *This = impl_from_IPersistStorage(iface);
1550 return IPersistStorage_Save(This->dataCache_PersistStg, pStgSave, fSaveAsLoad);
1554 /************************************************************************
1555 * DefaultHandler_IPersistStorage_SaveCompleted
1558 static HRESULT WINAPI DefaultHandler_IPersistStorage_SaveCompleted(
1559 IPersistStorage* iface,
1562 DefaultHandler *This = impl_from_IPersistStorage(iface);
1564 return IPersistStorage_SaveCompleted(This->dataCache_PersistStg, pStgNew);
1568 /************************************************************************
1569 * DefaultHandler_IPersistStorage_HandsOffStorage
1572 static HRESULT WINAPI DefaultHandler_IPersistStorage_HandsOffStorage(
1573 IPersistStorage* iface)
1575 DefaultHandler *This = impl_from_IPersistStorage(iface);
1577 return IPersistStorage_HandsOffStorage(This->dataCache_PersistStg);
1582 * Virtual function tables for the DefaultHandler class.
1584 static const IOleObjectVtbl DefaultHandler_IOleObject_VTable =
1586 DefaultHandler_QueryInterface,
1587 DefaultHandler_AddRef,
1588 DefaultHandler_Release,
1589 DefaultHandler_SetClientSite,
1590 DefaultHandler_GetClientSite,
1591 DefaultHandler_SetHostNames,
1592 DefaultHandler_Close,
1593 DefaultHandler_SetMoniker,
1594 DefaultHandler_GetMoniker,
1595 DefaultHandler_InitFromData,
1596 DefaultHandler_GetClipboardData,
1597 DefaultHandler_DoVerb,
1598 DefaultHandler_EnumVerbs,
1599 DefaultHandler_Update,
1600 DefaultHandler_IsUpToDate,
1601 DefaultHandler_GetUserClassID,
1602 DefaultHandler_GetUserType,
1603 DefaultHandler_SetExtent,
1604 DefaultHandler_GetExtent,
1605 DefaultHandler_Advise,
1606 DefaultHandler_Unadvise,
1607 DefaultHandler_EnumAdvise,
1608 DefaultHandler_GetMiscStatus,
1609 DefaultHandler_SetColorScheme
1612 static const IUnknownVtbl DefaultHandler_NDIUnknown_VTable =
1614 DefaultHandler_NDIUnknown_QueryInterface,
1615 DefaultHandler_NDIUnknown_AddRef,
1616 DefaultHandler_NDIUnknown_Release,
1619 static const IDataObjectVtbl DefaultHandler_IDataObject_VTable =
1621 DefaultHandler_IDataObject_QueryInterface,
1622 DefaultHandler_IDataObject_AddRef,
1623 DefaultHandler_IDataObject_Release,
1624 DefaultHandler_GetData,
1625 DefaultHandler_GetDataHere,
1626 DefaultHandler_QueryGetData,
1627 DefaultHandler_GetCanonicalFormatEtc,
1628 DefaultHandler_SetData,
1629 DefaultHandler_EnumFormatEtc,
1630 DefaultHandler_DAdvise,
1631 DefaultHandler_DUnadvise,
1632 DefaultHandler_EnumDAdvise
1635 static const IRunnableObjectVtbl DefaultHandler_IRunnableObject_VTable =
1637 DefaultHandler_IRunnableObject_QueryInterface,
1638 DefaultHandler_IRunnableObject_AddRef,
1639 DefaultHandler_IRunnableObject_Release,
1640 DefaultHandler_GetRunningClass,
1642 DefaultHandler_IsRunning,
1643 DefaultHandler_LockRunning,
1644 DefaultHandler_SetContainedObject
1647 static const IAdviseSinkVtbl DefaultHandler_IAdviseSink_VTable =
1649 DefaultHandler_IAdviseSink_QueryInterface,
1650 DefaultHandler_IAdviseSink_AddRef,
1651 DefaultHandler_IAdviseSink_Release,
1652 DefaultHandler_IAdviseSink_OnDataChange,
1653 DefaultHandler_IAdviseSink_OnViewChange,
1654 DefaultHandler_IAdviseSink_OnRename,
1655 DefaultHandler_IAdviseSink_OnSave,
1656 DefaultHandler_IAdviseSink_OnClose
1659 static const IPersistStorageVtbl DefaultHandler_IPersistStorage_VTable =
1661 DefaultHandler_IPersistStorage_QueryInterface,
1662 DefaultHandler_IPersistStorage_AddRef,
1663 DefaultHandler_IPersistStorage_Release,
1664 DefaultHandler_IPersistStorage_GetClassID,
1665 DefaultHandler_IPersistStorage_IsDirty,
1666 DefaultHandler_IPersistStorage_InitNew,
1667 DefaultHandler_IPersistStorage_Load,
1668 DefaultHandler_IPersistStorage_Save,
1669 DefaultHandler_IPersistStorage_SaveCompleted,
1670 DefaultHandler_IPersistStorage_HandsOffStorage
1673 /*********************************************************
1674 * Methods implementation for the DefaultHandler class.
1676 static DefaultHandler* DefaultHandler_Construct(
1678 LPUNKNOWN pUnkOuter)
1680 DefaultHandler* This = NULL;
1683 This = HeapAlloc(GetProcessHeap(), 0, sizeof(DefaultHandler));
1688 This->lpVtbl = &DefaultHandler_IOleObject_VTable;
1689 This->lpvtblIUnknown = &DefaultHandler_NDIUnknown_VTable;
1690 This->lpvtblIDataObject = &DefaultHandler_IDataObject_VTable;
1691 This->lpvtblIRunnableObject = &DefaultHandler_IRunnableObject_VTable;
1692 This->lpvtblIAdviseSink = &DefaultHandler_IAdviseSink_VTable;
1693 This->lpvtblIPersistStorage = &DefaultHandler_IPersistStorage_VTable;
1696 * Start with one reference count. The caller of this function
1697 * must release the interface pointer when it is done.
1702 * Initialize the outer unknown
1703 * We don't keep a reference on the outer unknown since, the way
1704 * aggregation works, our lifetime is at least as large as its
1708 pUnkOuter = (IUnknown*)&This->lpvtblIUnknown;
1710 This->outerUnknown = pUnkOuter;
1713 * Create a datacache object.
1714 * We aggregate with the datacache. Make sure we pass our outer
1715 * unknown as the datacache's outer unknown.
1717 hr = CreateDataCache(This->outerUnknown,
1720 (void**)&This->dataCache);
1722 hr = IUnknown_QueryInterface(This->dataCache, &IID_IPersistStorage, (void**)&This->dataCache_PersistStg);
1724 ERR("Unexpected error creating data cache\n");
1726 This->clsid = *clsid;
1727 This->clientSite = NULL;
1728 This->oleAdviseHolder = NULL;
1729 This->dataAdviseHolder = NULL;
1730 This->containerApp = NULL;
1731 This->containerObj = NULL;
1732 This->pOleDelegate = NULL;
1733 This->pPSDelegate = NULL;
1734 This->pDataDelegate = NULL;
1736 This->dwAdvConn = 0;
1741 static void DefaultHandler_Destroy(
1742 DefaultHandler* This)
1744 /* release delegates */
1745 DefaultHandler_Stop(This);
1747 HeapFree( GetProcessHeap(), 0, This->containerApp );
1748 This->containerApp = NULL;
1749 HeapFree( GetProcessHeap(), 0, This->containerObj );
1750 This->containerObj = NULL;
1752 if (This->dataCache)
1754 IPersistStorage_Release(This->dataCache_PersistStg);
1755 IUnknown_Release(This->dataCache);
1756 This->dataCache_PersistStg = NULL;
1757 This->dataCache = NULL;
1760 if (This->clientSite)
1762 IOleClientSite_Release(This->clientSite);
1763 This->clientSite = NULL;
1766 if (This->oleAdviseHolder)
1768 IOleAdviseHolder_Release(This->oleAdviseHolder);
1769 This->oleAdviseHolder = NULL;
1772 if (This->dataAdviseHolder)
1774 IDataAdviseHolder_Release(This->dataAdviseHolder);
1775 This->dataAdviseHolder = NULL;
1778 HeapFree(GetProcessHeap(), 0, This);
1781 /******************************************************************************
1782 * OleCreateDefaultHandler [OLE32.@]
1784 HRESULT WINAPI OleCreateDefaultHandler(
1786 LPUNKNOWN pUnkOuter,
1790 DefaultHandler* newHandler = NULL;
1793 TRACE("(%s, %p, %s, %p)\n", debugstr_guid(clsid), pUnkOuter, debugstr_guid(riid), ppvObj);
1801 * If This handler is constructed for aggregation, make sure
1802 * the caller is requesting the IUnknown interface.
1803 * This is necessary because it's the only time the non-delegating
1804 * IUnknown pointer can be returned to the outside.
1806 if (pUnkOuter && !IsEqualIID(&IID_IUnknown, riid))
1807 return CLASS_E_NOAGGREGATION;
1810 * Try to construct a new instance of the class.
1812 newHandler = DefaultHandler_Construct(clsid, pUnkOuter);
1815 return E_OUTOFMEMORY;
1818 * Make sure it supports the interface required by the caller.
1820 hr = IUnknown_QueryInterface((IUnknown*)&newHandler->lpvtblIUnknown, riid, ppvObj);
1823 * Release the reference obtained in the constructor. If
1824 * the QueryInterface was unsuccessful, it will free the class.
1826 IUnknown_Release((IUnknown*)&newHandler->lpvtblIUnknown);