1*84344399STimo Kreuzer /** 2*84344399STimo Kreuzer * This file has no copyright assigned and is placed in the Public Domain. 3*84344399STimo Kreuzer * This file is part of the mingw-w64 runtime package. 4*84344399STimo Kreuzer * No warranty is given; refer to the file DISCLAIMER.PD within this package. 5*84344399STimo Kreuzer */ 6*84344399STimo Kreuzer #ifndef _INC_COMIP 7*84344399STimo Kreuzer #define _INC_COMIP 8*84344399STimo Kreuzer 9*84344399STimo Kreuzer #include <_mingw.h> 10*84344399STimo Kreuzer 11*84344399STimo Kreuzer #include <ole2.h> 12*84344399STimo Kreuzer #include <malloc.h> 13*84344399STimo Kreuzer 14*84344399STimo Kreuzer #include <comutil.h> 15*84344399STimo Kreuzer 16*84344399STimo Kreuzer #ifdef __cplusplus 17*84344399STimo Kreuzer 18*84344399STimo Kreuzer #pragma push_macro("new") 19*84344399STimo Kreuzer #undef new 20*84344399STimo Kreuzer 21*84344399STimo Kreuzer #include <new.h> 22*84344399STimo Kreuzer 23*84344399STimo Kreuzer class _com_error; 24*84344399STimo Kreuzer 25*84344399STimo Kreuzer #ifndef WINAPI 26*84344399STimo Kreuzer #define WINAPI __stdcall 27*84344399STimo Kreuzer #endif 28*84344399STimo Kreuzer 29*84344399STimo Kreuzer void WINAPI _com_issue_error(HRESULT); 30*84344399STimo Kreuzer struct IUnknown; 31*84344399STimo Kreuzer 32*84344399STimo Kreuzer template<typename _Interface,const IID *_IID > 33*84344399STimo Kreuzer class _com_IIID { 34*84344399STimo Kreuzer public: 35*84344399STimo Kreuzer typedef _Interface Interface; GetInterfacePtr()36*84344399STimo Kreuzer static _Interface *GetInterfacePtr() throw() { return NULL; } GetInterface()37*84344399STimo Kreuzer static _Interface& GetInterface() throw() { return *GetInterfacePtr(); } GetIID()38*84344399STimo Kreuzer static const IID& GetIID() throw() { return *_IID; } 39*84344399STimo Kreuzer }; 40*84344399STimo Kreuzer 41*84344399STimo Kreuzer template<typename _IIID> class _com_ptr_t { 42*84344399STimo Kreuzer public: 43*84344399STimo Kreuzer typedef _IIID ThisIIID; 44*84344399STimo Kreuzer typedef typename _IIID::Interface Interface; GetIID()45*84344399STimo Kreuzer static const IID& GetIID() throw() { return ThisIIID::GetIID(); } _com_ptr_t(const _com_ptr_t<_OtherIID> & p)46*84344399STimo Kreuzer template<typename _OtherIID> _com_ptr_t(const _com_ptr_t<_OtherIID> &p) : m_pInterface(NULL) { 47*84344399STimo Kreuzer HRESULT hr = _QueryInterface(p); 48*84344399STimo Kreuzer if(FAILED(hr) && (hr!=E_NOINTERFACE)) { _com_issue_error(hr); } 49*84344399STimo Kreuzer } _com_ptr_t(_InterfaceType * p)50*84344399STimo Kreuzer template<typename _InterfaceType> _com_ptr_t(_InterfaceType *p) : m_pInterface(NULL) { 51*84344399STimo Kreuzer HRESULT hr = _QueryInterface(p); 52*84344399STimo Kreuzer if(FAILED(hr) && (hr!=E_NOINTERFACE)) { _com_issue_error(hr); } 53*84344399STimo Kreuzer } _com_ptr_t(LPSTR str)54*84344399STimo Kreuzer template<typename _X> _com_ptr_t(LPSTR str) { new(this) _com_ptr_t(static_cast<LPCSTR> (str),NULL); } _com_ptr_t(LPWSTR str)55*84344399STimo Kreuzer template<typename _X> _com_ptr_t(LPWSTR str) { new(this) _com_ptr_t(static_cast<LPCWSTR> (str),NULL); } _com_ptr_t(_com_ptr_t * p)56*84344399STimo Kreuzer template<typename _X> explicit _com_ptr_t(_com_ptr_t *p) : m_pInterface(NULL) { 57*84344399STimo Kreuzer if(!p) { _com_issue_error(E_POINTER); } 58*84344399STimo Kreuzer else { 59*84344399STimo Kreuzer m_pInterface = p->m_pInterface; 60*84344399STimo Kreuzer AddRef(); 61*84344399STimo Kreuzer } 62*84344399STimo Kreuzer } throw()63*84344399STimo Kreuzer _com_ptr_t() throw() : m_pInterface(NULL) { } _com_ptr_t(int null)64*84344399STimo Kreuzer _com_ptr_t(int null) : m_pInterface(NULL) { 65*84344399STimo Kreuzer if(null!=0) { _com_issue_error(E_POINTER); } 66*84344399STimo Kreuzer } 67*84344399STimo Kreuzer 68*84344399STimo Kreuzer #ifdef _NATIVE_NULLPTR_SUPPORTED _com_ptr_t(decltype (nullptr))69*84344399STimo Kreuzer _com_ptr_t(decltype(nullptr)) : m_pInterface(NULL) {} 70*84344399STimo Kreuzer #endif 71*84344399STimo Kreuzer throw()72*84344399STimo Kreuzer _com_ptr_t(const _com_ptr_t &cp) throw() : m_pInterface(cp.m_pInterface) { _AddRef(); } _com_ptr_t(Interface * pInterface)73*84344399STimo Kreuzer template<typename _X> _com_ptr_t(Interface *pInterface) throw() : m_pInterface(pInterface) { _AddRef(); } _com_ptr_t(Interface * pInterface,bool fAddRef)74*84344399STimo Kreuzer _com_ptr_t(Interface *pInterface,bool fAddRef) throw() : m_pInterface(pInterface) { 75*84344399STimo Kreuzer if(fAddRef) _AddRef(); 76*84344399STimo Kreuzer } _com_ptr_t(const _variant_t & varSrc)77*84344399STimo Kreuzer _com_ptr_t(const _variant_t& varSrc) : m_pInterface(NULL) { 78*84344399STimo Kreuzer HRESULT hr = QueryStdInterfaces(varSrc); 79*84344399STimo Kreuzer if(FAILED(hr) && (hr!=E_NOINTERFACE)) { _com_issue_error(hr); } 80*84344399STimo Kreuzer } m_pInterface(NULL)81*84344399STimo Kreuzer explicit _com_ptr_t(const CLSID &clsid,IUnknown *pOuter = NULL,DWORD dwClsContext = CLSCTX_ALL) : m_pInterface(NULL) { 82*84344399STimo Kreuzer HRESULT hr = CreateInstance(clsid,pOuter,dwClsContext); 83*84344399STimo Kreuzer if(FAILED(hr) && (hr!=E_NOINTERFACE)) { _com_issue_error(hr); } 84*84344399STimo Kreuzer } m_pInterface(NULL)85*84344399STimo Kreuzer explicit _com_ptr_t(LPCWSTR str,IUnknown *pOuter = NULL,DWORD dwClsContext = CLSCTX_ALL) : m_pInterface(NULL) { 86*84344399STimo Kreuzer HRESULT hr = CreateInstance(str,pOuter,dwClsContext); 87*84344399STimo Kreuzer if(FAILED(hr) && (hr!=E_NOINTERFACE)) { _com_issue_error(hr); } 88*84344399STimo Kreuzer } m_pInterface(NULL)89*84344399STimo Kreuzer explicit _com_ptr_t(LPCSTR str,IUnknown *pOuter = NULL,DWORD dwClsContext = CLSCTX_ALL) : m_pInterface(NULL) { 90*84344399STimo Kreuzer HRESULT hr = CreateInstance(str,pOuter,dwClsContext); 91*84344399STimo Kreuzer if(FAILED(hr) && (hr!=E_NOINTERFACE)) { _com_issue_error(hr); } 92*84344399STimo Kreuzer } 93*84344399STimo Kreuzer template<typename _OtherIID> _com_ptr_t &operator=(const _com_ptr_t<_OtherIID> &p) { 94*84344399STimo Kreuzer HRESULT hr = _QueryInterface(p); 95*84344399STimo Kreuzer if(FAILED(hr) && (hr!=E_NOINTERFACE)) { _com_issue_error(hr); } 96*84344399STimo Kreuzer return *this; 97*84344399STimo Kreuzer } 98*84344399STimo Kreuzer template<typename _InterfaceType> _com_ptr_t &operator=(_InterfaceType *p) { 99*84344399STimo Kreuzer HRESULT hr = _QueryInterface(p); 100*84344399STimo Kreuzer if(FAILED(hr) && (hr!=E_NOINTERFACE)) { _com_issue_error(hr); } 101*84344399STimo Kreuzer return *this; 102*84344399STimo Kreuzer } throw()103*84344399STimo Kreuzer template<typename _X> _com_ptr_t &operator=(Interface *pInterface) throw() { 104*84344399STimo Kreuzer if(m_pInterface!=pInterface) { 105*84344399STimo Kreuzer Interface *pOldInterface = m_pInterface; 106*84344399STimo Kreuzer m_pInterface = pInterface; 107*84344399STimo Kreuzer _AddRef(); 108*84344399STimo Kreuzer if(pOldInterface!=NULL) pOldInterface->Release(); 109*84344399STimo Kreuzer } 110*84344399STimo Kreuzer return *this; 111*84344399STimo Kreuzer } throw()112*84344399STimo Kreuzer _com_ptr_t &operator=(const _com_ptr_t &cp) throw() { return operator=(cp.m_pInterface); } 113*84344399STimo Kreuzer _com_ptr_t &operator=(int null) { 114*84344399STimo Kreuzer if(null!=0) { _com_issue_error(E_POINTER); } 115*84344399STimo Kreuzer return operator=(reinterpret_cast<Interface*>(NULL)); 116*84344399STimo Kreuzer } 117*84344399STimo Kreuzer _com_ptr_t &operator=(const _variant_t& varSrc) { 118*84344399STimo Kreuzer HRESULT hr = QueryStdInterfaces(varSrc); 119*84344399STimo Kreuzer if(FAILED(hr) && (hr!=E_NOINTERFACE)) { _com_issue_error(hr); } 120*84344399STimo Kreuzer return *this; 121*84344399STimo Kreuzer } throw()122*84344399STimo Kreuzer ~_com_ptr_t() throw() { _Release(); } Attach(Interface * pInterface)123*84344399STimo Kreuzer void Attach(Interface *pInterface) throw() { 124*84344399STimo Kreuzer _Release(); 125*84344399STimo Kreuzer m_pInterface = pInterface; 126*84344399STimo Kreuzer } Attach(Interface * pInterface,bool fAddRef)127*84344399STimo Kreuzer void Attach(Interface *pInterface,bool fAddRef) throw() { 128*84344399STimo Kreuzer _Release(); 129*84344399STimo Kreuzer m_pInterface = pInterface; 130*84344399STimo Kreuzer if(fAddRef) { 131*84344399STimo Kreuzer if(!pInterface) { _com_issue_error(E_POINTER); } 132*84344399STimo Kreuzer else pInterface->AddRef(); 133*84344399STimo Kreuzer } 134*84344399STimo Kreuzer } Detach()135*84344399STimo Kreuzer Interface *Detach() throw() { 136*84344399STimo Kreuzer Interface *const old = m_pInterface; 137*84344399STimo Kreuzer m_pInterface = NULL; 138*84344399STimo Kreuzer return old; 139*84344399STimo Kreuzer } throw()140*84344399STimo Kreuzer operator Interface*() const throw() { return m_pInterface; } 141*84344399STimo Kreuzer operator Interface&() const { 142*84344399STimo Kreuzer if(!m_pInterface) { _com_issue_error(E_POINTER); } 143*84344399STimo Kreuzer return *m_pInterface; 144*84344399STimo Kreuzer } 145*84344399STimo Kreuzer Interface& operator*() const { 146*84344399STimo Kreuzer if(!m_pInterface) { _com_issue_error(E_POINTER); } 147*84344399STimo Kreuzer return *m_pInterface; 148*84344399STimo Kreuzer } throw()149*84344399STimo Kreuzer Interface **operator&() throw() { 150*84344399STimo Kreuzer _Release(); 151*84344399STimo Kreuzer m_pInterface = NULL; 152*84344399STimo Kreuzer return &m_pInterface; 153*84344399STimo Kreuzer } 154*84344399STimo Kreuzer Interface *operator->() const { 155*84344399STimo Kreuzer if(!m_pInterface) { _com_issue_error(E_POINTER); } 156*84344399STimo Kreuzer return m_pInterface; 157*84344399STimo Kreuzer } throw()158*84344399STimo Kreuzer operator bool() const throw() { return m_pInterface!=NULL; } 159*84344399STimo Kreuzer template<typename _OtherIID> bool operator==(const _com_ptr_t<_OtherIID> &p) { return _CompareUnknown(p)==0; } 160*84344399STimo Kreuzer template<typename _OtherIID> bool operator==(_com_ptr_t<_OtherIID> &p) { return _CompareUnknown(p)==0; } 161*84344399STimo Kreuzer template<typename _InterfaceType> bool operator==(_InterfaceType *p) { return _CompareUnknown(p)==0; } 162*84344399STimo Kreuzer template<typename _X> bool operator==(Interface *p) { return (m_pInterface==p) ? true : _CompareUnknown(p)==0; } 163*84344399STimo Kreuzer template<typename _X> bool operator==(const _com_ptr_t &p) throw() { return operator==(p.m_pInterface); } 164*84344399STimo Kreuzer template<typename _X> bool operator==(_com_ptr_t &p) throw() { return operator==(p.m_pInterface); } 165*84344399STimo Kreuzer bool operator==(int null) { 166*84344399STimo Kreuzer if(null!=0) { _com_issue_error(E_POINTER); } 167*84344399STimo Kreuzer return !m_pInterface; 168*84344399STimo Kreuzer } 169*84344399STimo Kreuzer template<typename _OtherIID> bool operator!=(const _com_ptr_t<_OtherIID> &p) { return !(operator==(p)); } 170*84344399STimo Kreuzer template<typename _OtherIID> bool operator!=(_com_ptr_t<_OtherIID> &p) { return !(operator==(p)); } 171*84344399STimo Kreuzer template<typename _InterfaceType> bool operator!=(_InterfaceType *p) { return !(operator==(p)); } 172*84344399STimo Kreuzer bool operator!=(int null) { return !(operator==(null)); } 173*84344399STimo Kreuzer template<typename _OtherIID> bool operator<(const _com_ptr_t<_OtherIID> &p) { return _CompareUnknown(p)<0; } 174*84344399STimo Kreuzer template<typename _OtherIID> bool operator<(_com_ptr_t<_OtherIID> &p) { return _CompareUnknown(p)<0; } 175*84344399STimo Kreuzer template<typename _InterfaceType> bool operator<(_InterfaceType *p) { return _CompareUnknown(p)<0; } 176*84344399STimo Kreuzer template<typename _OtherIID> bool operator>(const _com_ptr_t<_OtherIID> &p) { return _CompareUnknown(p)>0; } 177*84344399STimo Kreuzer template<typename _OtherIID> bool operator>(_com_ptr_t<_OtherIID> &p) { return _CompareUnknown(p)>0; } 178*84344399STimo Kreuzer template<typename _InterfaceType> bool operator>(_InterfaceType *p) { return _CompareUnknown(p)>0; } 179*84344399STimo Kreuzer template<typename _OtherIID> bool operator<=(const _com_ptr_t<_OtherIID> &p) { return _CompareUnknown(p)<=0; } 180*84344399STimo Kreuzer template<typename _OtherIID> bool operator<=(_com_ptr_t<_OtherIID> &p) { return _CompareUnknown(p)<=0; } 181*84344399STimo Kreuzer template<typename _InterfaceType> bool operator<=(_InterfaceType *p) { return _CompareUnknown(p)<=0; } 182*84344399STimo Kreuzer template<typename _OtherIID> bool operator>=(const _com_ptr_t<_OtherIID> &p) { return _CompareUnknown(p)>=0; } 183*84344399STimo Kreuzer template<typename _OtherIID> bool operator>=(_com_ptr_t<_OtherIID> &p) { return _CompareUnknown(p)>=0; } 184*84344399STimo Kreuzer template<typename _InterfaceType> bool operator>=(_InterfaceType *p) { return _CompareUnknown(p)>=0; } Release()185*84344399STimo Kreuzer void Release() { 186*84344399STimo Kreuzer if(!m_pInterface) { _com_issue_error(E_POINTER); } 187*84344399STimo Kreuzer else { 188*84344399STimo Kreuzer m_pInterface->Release(); 189*84344399STimo Kreuzer m_pInterface = NULL; 190*84344399STimo Kreuzer } 191*84344399STimo Kreuzer } AddRef()192*84344399STimo Kreuzer void AddRef() { 193*84344399STimo Kreuzer if(!m_pInterface) { _com_issue_error(E_POINTER); } 194*84344399STimo Kreuzer else m_pInterface->AddRef(); 195*84344399STimo Kreuzer } GetInterfacePtr()196*84344399STimo Kreuzer Interface *GetInterfacePtr() const throw() { return m_pInterface; } GetInterfacePtr()197*84344399STimo Kreuzer Interface*& GetInterfacePtr() throw() { return m_pInterface; } throw()198*84344399STimo Kreuzer HRESULT CreateInstance(const CLSID &rclsid,IUnknown *pOuter = NULL,DWORD dwClsContext = CLSCTX_ALL) throw() { 199*84344399STimo Kreuzer HRESULT hr; 200*84344399STimo Kreuzer _Release(); 201*84344399STimo Kreuzer if(dwClsContext & (CLSCTX_LOCAL_SERVER | CLSCTX_REMOTE_SERVER)) { 202*84344399STimo Kreuzer IUnknown *pIUnknown; 203*84344399STimo Kreuzer hr = CoCreateInstance(rclsid,pOuter,dwClsContext,IID_IUnknown,reinterpret_cast<void**>(&pIUnknown)); 204*84344399STimo Kreuzer if(SUCCEEDED(hr)) { 205*84344399STimo Kreuzer hr = OleRun(pIUnknown); 206*84344399STimo Kreuzer if(SUCCEEDED(hr)) hr = pIUnknown->QueryInterface(GetIID(),reinterpret_cast<void**>(&m_pInterface)); 207*84344399STimo Kreuzer pIUnknown->Release(); 208*84344399STimo Kreuzer } 209*84344399STimo Kreuzer } else hr = CoCreateInstance(rclsid,pOuter,dwClsContext,GetIID(),reinterpret_cast<void**>(&m_pInterface)); 210*84344399STimo Kreuzer if(FAILED(hr)) m_pInterface = NULL; 211*84344399STimo Kreuzer return hr; 212*84344399STimo Kreuzer } throw()213*84344399STimo Kreuzer HRESULT CreateInstance(LPCWSTR clsidString,IUnknown *pOuter = NULL,DWORD dwClsContext = CLSCTX_ALL) throw() { 214*84344399STimo Kreuzer if(!clsidString) return E_INVALIDARG; 215*84344399STimo Kreuzer CLSID clsid; 216*84344399STimo Kreuzer HRESULT hr; 217*84344399STimo Kreuzer if(clsidString[0]==L'{') hr = CLSIDFromString(const_cast<LPWSTR> (clsidString),&clsid); 218*84344399STimo Kreuzer else hr = CLSIDFromProgID(const_cast<LPWSTR> (clsidString),&clsid); 219*84344399STimo Kreuzer if(FAILED(hr)) return hr; 220*84344399STimo Kreuzer return CreateInstance(clsid,pOuter,dwClsContext); 221*84344399STimo Kreuzer } throw()222*84344399STimo Kreuzer HRESULT CreateInstance(LPCSTR clsidStringA,IUnknown *pOuter = NULL,DWORD dwClsContext = CLSCTX_ALL) throw() { 223*84344399STimo Kreuzer if(!clsidStringA) return E_INVALIDARG; 224*84344399STimo Kreuzer int size = lstrlenA(clsidStringA) + 1; 225*84344399STimo Kreuzer int destSize = MultiByteToWideChar(CP_ACP,0,clsidStringA,size,NULL,0); 226*84344399STimo Kreuzer if(destSize==0) return HRESULT_FROM_WIN32(GetLastError()); 227*84344399STimo Kreuzer LPWSTR clsidStringW; 228*84344399STimo Kreuzer clsidStringW = static_cast<LPWSTR>(_malloca(destSize*sizeof(WCHAR))); 229*84344399STimo Kreuzer if(!clsidStringW) return E_OUTOFMEMORY; 230*84344399STimo Kreuzer if(MultiByteToWideChar(CP_ACP,0,clsidStringA,size,clsidStringW,destSize)==0) { 231*84344399STimo Kreuzer _freea(clsidStringW); 232*84344399STimo Kreuzer return HRESULT_FROM_WIN32(GetLastError()); 233*84344399STimo Kreuzer } 234*84344399STimo Kreuzer HRESULT hr=CreateInstance(clsidStringW,pOuter,dwClsContext); 235*84344399STimo Kreuzer _freea(clsidStringW); 236*84344399STimo Kreuzer return hr; 237*84344399STimo Kreuzer } GetActiveObject(const CLSID & rclsid)238*84344399STimo Kreuzer HRESULT GetActiveObject(const CLSID &rclsid) throw() { 239*84344399STimo Kreuzer _Release(); 240*84344399STimo Kreuzer IUnknown *pIUnknown; 241*84344399STimo Kreuzer HRESULT hr = ::GetActiveObject(rclsid,NULL,&pIUnknown); 242*84344399STimo Kreuzer if(SUCCEEDED(hr)) { 243*84344399STimo Kreuzer hr = pIUnknown->QueryInterface(GetIID(),reinterpret_cast<void**>(&m_pInterface)); 244*84344399STimo Kreuzer pIUnknown->Release(); 245*84344399STimo Kreuzer } 246*84344399STimo Kreuzer if(FAILED(hr)) m_pInterface = NULL; 247*84344399STimo Kreuzer return hr; 248*84344399STimo Kreuzer } GetActiveObject(LPCWSTR clsidString)249*84344399STimo Kreuzer HRESULT GetActiveObject(LPCWSTR clsidString) throw() { 250*84344399STimo Kreuzer if(!clsidString) return E_INVALIDARG; 251*84344399STimo Kreuzer CLSID clsid; 252*84344399STimo Kreuzer HRESULT hr; 253*84344399STimo Kreuzer if(clsidString[0]=='{') hr = CLSIDFromString(const_cast<LPWSTR> (clsidString),&clsid); 254*84344399STimo Kreuzer else hr = CLSIDFromProgID(const_cast<LPWSTR> (clsidString),&clsid); 255*84344399STimo Kreuzer if(FAILED(hr)) return hr; 256*84344399STimo Kreuzer return GetActiveObject(clsid); 257*84344399STimo Kreuzer } GetActiveObject(LPCSTR clsidStringA)258*84344399STimo Kreuzer HRESULT GetActiveObject(LPCSTR clsidStringA) throw() { 259*84344399STimo Kreuzer if(!clsidStringA) return E_INVALIDARG; 260*84344399STimo Kreuzer int size = lstrlenA(clsidStringA) + 1; 261*84344399STimo Kreuzer int destSize = MultiByteToWideChar(CP_ACP,0,clsidStringA,size,NULL,0); 262*84344399STimo Kreuzer LPWSTR clsidStringW; 263*84344399STimo Kreuzer try { 264*84344399STimo Kreuzer clsidStringW = static_cast<LPWSTR>(_alloca(destSize*sizeof(WCHAR))); 265*84344399STimo Kreuzer } catch (...) { 266*84344399STimo Kreuzer clsidStringW = NULL; 267*84344399STimo Kreuzer } 268*84344399STimo Kreuzer if(!clsidStringW) return E_OUTOFMEMORY; 269*84344399STimo Kreuzer if(MultiByteToWideChar(CP_ACP,0,clsidStringA,size,clsidStringW,destSize)==0) return HRESULT_FROM_WIN32(GetLastError()); 270*84344399STimo Kreuzer return GetActiveObject(clsidStringW); 271*84344399STimo Kreuzer } QueryInterface(const IID & iid,_InterfaceType * & p)272*84344399STimo Kreuzer template<typename _InterfaceType> HRESULT QueryInterface(const IID& iid,_InterfaceType*& p) throw () { 273*84344399STimo Kreuzer if(m_pInterface!=NULL) return m_pInterface->QueryInterface(iid,reinterpret_cast<void**>(&p)); 274*84344399STimo Kreuzer return E_POINTER; 275*84344399STimo Kreuzer } QueryInterface(const IID & iid,_InterfaceType ** p)276*84344399STimo Kreuzer template<typename _InterfaceType> HRESULT QueryInterface(const IID& iid,_InterfaceType **p) throw() { return QueryInterface(iid,*p); } 277*84344399STimo Kreuzer private: 278*84344399STimo Kreuzer Interface *m_pInterface; _Release()279*84344399STimo Kreuzer void _Release() throw() { 280*84344399STimo Kreuzer if(m_pInterface!=NULL) m_pInterface->Release(); 281*84344399STimo Kreuzer } _AddRef()282*84344399STimo Kreuzer void _AddRef() throw() { 283*84344399STimo Kreuzer if(m_pInterface!=NULL) m_pInterface->AddRef(); 284*84344399STimo Kreuzer } _QueryInterface(_InterfacePtr p)285*84344399STimo Kreuzer template<typename _InterfacePtr> HRESULT _QueryInterface(_InterfacePtr p) throw() { 286*84344399STimo Kreuzer HRESULT hr; 287*84344399STimo Kreuzer if(p!=NULL) { 288*84344399STimo Kreuzer Interface *pInterface; 289*84344399STimo Kreuzer hr = p->QueryInterface(GetIID(),reinterpret_cast<void**>(&pInterface)); 290*84344399STimo Kreuzer Attach(SUCCEEDED(hr)? pInterface: NULL); 291*84344399STimo Kreuzer } else { 292*84344399STimo Kreuzer operator=(static_cast<Interface*>(NULL)); 293*84344399STimo Kreuzer hr = E_NOINTERFACE; 294*84344399STimo Kreuzer } 295*84344399STimo Kreuzer return hr; 296*84344399STimo Kreuzer } _CompareUnknown(_InterfacePtr p)297*84344399STimo Kreuzer template<typename _InterfacePtr> int _CompareUnknown(_InterfacePtr p) { 298*84344399STimo Kreuzer IUnknown *pu1,*pu2; 299*84344399STimo Kreuzer if(m_pInterface!=NULL) { 300*84344399STimo Kreuzer HRESULT hr = m_pInterface->QueryInterface(IID_IUnknown,reinterpret_cast<void**>(&pu1)); 301*84344399STimo Kreuzer if(FAILED(hr)) { 302*84344399STimo Kreuzer _com_issue_error(hr); 303*84344399STimo Kreuzer pu1 = NULL; 304*84344399STimo Kreuzer } else pu1->Release(); 305*84344399STimo Kreuzer } else pu1 = NULL; 306*84344399STimo Kreuzer if(p!=NULL) { 307*84344399STimo Kreuzer HRESULT hr = p->QueryInterface(IID_IUnknown,reinterpret_cast<void**>(&pu2)); 308*84344399STimo Kreuzer if(FAILED(hr)) { 309*84344399STimo Kreuzer _com_issue_error(hr); 310*84344399STimo Kreuzer pu2 = NULL; 311*84344399STimo Kreuzer } else pu2->Release(); 312*84344399STimo Kreuzer } else pu2 = NULL; 313*84344399STimo Kreuzer return pu1 - pu2; 314*84344399STimo Kreuzer } QueryStdInterfaces(const _variant_t & varSrc)315*84344399STimo Kreuzer HRESULT QueryStdInterfaces(const _variant_t& varSrc) throw() { 316*84344399STimo Kreuzer if(V_VT(&varSrc)==VT_DISPATCH) return _QueryInterface(V_DISPATCH(&varSrc)); 317*84344399STimo Kreuzer if(V_VT(&varSrc)==VT_UNKNOWN) return _QueryInterface(V_UNKNOWN(&varSrc)); 318*84344399STimo Kreuzer VARIANT varDest; 319*84344399STimo Kreuzer VariantInit(&varDest); 320*84344399STimo Kreuzer HRESULT hr = VariantChangeType(&varDest,const_cast<VARIANT*>(static_cast<const VARIANT*>(&varSrc)),0,VT_DISPATCH); 321*84344399STimo Kreuzer if(SUCCEEDED(hr)) hr = _QueryInterface(V_DISPATCH(&varSrc)); 322*84344399STimo Kreuzer if(hr==E_NOINTERFACE) { 323*84344399STimo Kreuzer VariantInit(&varDest); 324*84344399STimo Kreuzer hr = VariantChangeType(&varDest,const_cast<VARIANT*>(static_cast<const VARIANT*>(&varSrc)),0,VT_UNKNOWN); 325*84344399STimo Kreuzer if(SUCCEEDED(hr)) hr = _QueryInterface(V_UNKNOWN(&varSrc)); 326*84344399STimo Kreuzer } 327*84344399STimo Kreuzer VariantClear(&varDest); 328*84344399STimo Kreuzer return hr; 329*84344399STimo Kreuzer } 330*84344399STimo Kreuzer }; 331*84344399STimo Kreuzer 332*84344399STimo Kreuzer template<typename _InterfaceType> bool operator==(int null,_com_ptr_t<_InterfaceType> &p) { 333*84344399STimo Kreuzer if(null!=0) { _com_issue_error(E_POINTER); } 334*84344399STimo Kreuzer return !p; 335*84344399STimo Kreuzer } 336*84344399STimo Kreuzer 337*84344399STimo Kreuzer template<typename _Interface,typename _InterfacePtr> bool operator==(_Interface *i,_com_ptr_t<_InterfacePtr> &p) { return p==i; } 338*84344399STimo Kreuzer 339*84344399STimo Kreuzer template<typename _Interface> bool operator!=(int null,_com_ptr_t<_Interface> &p) { 340*84344399STimo Kreuzer if(null!=0) { _com_issue_error(E_POINTER); } 341*84344399STimo Kreuzer return p!=NULL; 342*84344399STimo Kreuzer } 343*84344399STimo Kreuzer 344*84344399STimo Kreuzer template<typename _Interface,typename _InterfacePtr> bool operator!=(_Interface *i,_com_ptr_t<_InterfacePtr> &p) { return p!=i; } 345*84344399STimo Kreuzer 346*84344399STimo Kreuzer template<typename _Interface> bool operator<(int null,_com_ptr_t<_Interface> &p) { 347*84344399STimo Kreuzer if(null!=0) { _com_issue_error(E_POINTER); } 348*84344399STimo Kreuzer return p>NULL; 349*84344399STimo Kreuzer } 350*84344399STimo Kreuzer 351*84344399STimo Kreuzer template<typename _Interface,typename _InterfacePtr> bool operator<(_Interface *i,_com_ptr_t<_InterfacePtr> &p) { return p>i; } 352*84344399STimo Kreuzer 353*84344399STimo Kreuzer template<typename _Interface> bool operator>(int null,_com_ptr_t<_Interface> &p) { 354*84344399STimo Kreuzer if(null!=0) { _com_issue_error(E_POINTER); } 355*84344399STimo Kreuzer return p<NULL; 356*84344399STimo Kreuzer } 357*84344399STimo Kreuzer 358*84344399STimo Kreuzer template<typename _Interface,typename _InterfacePtr> bool operator>(_Interface *i,_com_ptr_t<_InterfacePtr> &p) { return p<i; } 359*84344399STimo Kreuzer 360*84344399STimo Kreuzer template<typename _Interface> bool operator<=(int null,_com_ptr_t<_Interface> &p) { 361*84344399STimo Kreuzer if(null!=0) { _com_issue_error(E_POINTER); } 362*84344399STimo Kreuzer return p>=NULL; 363*84344399STimo Kreuzer } 364*84344399STimo Kreuzer 365*84344399STimo Kreuzer template<typename _Interface,typename _InterfacePtr> bool operator<=(_Interface *i,_com_ptr_t<_InterfacePtr> &p) { return p>=i; } 366*84344399STimo Kreuzer 367*84344399STimo Kreuzer template<typename _Interface> bool operator>=(int null,_com_ptr_t<_Interface> &p) { 368*84344399STimo Kreuzer if(null!=0) { _com_issue_error(E_POINTER); } 369*84344399STimo Kreuzer return p<=NULL; 370*84344399STimo Kreuzer } 371*84344399STimo Kreuzer 372*84344399STimo Kreuzer template<typename _Interface,typename _InterfacePtr> bool operator>=(_Interface *i,_com_ptr_t<_InterfacePtr> &p) { return p<=i; } 373*84344399STimo Kreuzer 374*84344399STimo Kreuzer #pragma pop_macro("new") 375*84344399STimo Kreuzer 376*84344399STimo Kreuzer #endif /* __cplusplus */ 377*84344399STimo Kreuzer 378*84344399STimo Kreuzer #endif /* _INC_COMIP */ 379