// mbvimpl.h: Jonathan Borden's Marshal-by-Value implementation // Copyright (c) 1997 JABR Technology Corporation, all rights reserved // Jonathan Borden 3/26/97 // jborden@MEDIAONE.NET #pragma once template class ATL_NO_VTABLE IMarshalByValueImpl : public IMarshal { // this template is modified from don box's aggregatable MBV ... some MSJ issue // the template obviates the need for an aggregatable objectpublic: // IUnknown STDMETHOD(QueryInterface)(REFIID riid, void ** ppvObject) = 0; _ATL_DEBUG_ADDREF_RELEASE_IMPL(IMarshalByValueImpl) // IMarshal STDMETHODIMP GetUnmarshalClass(REFIID riid, void *pv, DWORD dwDestContext, void *pvDestContext, DWORD mshlflags, CLSID *pCid) { T* pT = static_cast(this); *pCid = pT->GetObjectCLSID(); return S_OK; } STDMETHODIMP GetMarshalSizeMax(REFIID riid, void *pv, DWORD dwDestContext, void *pvDestContext, DWORD mshlflags, DWORD *pSize) { // IPersistStream::GetSizeMax T* pT = static_cast(this); HRESULT hr = E_FAIL; ULARGE_INTEGER uli; hr = pT->GetSizeMax(&uli); if (SUCCEEDED(hr)) *pSize = uli.LowPart; return hr; } STDMETHODIMP MarshalInterface(IStream *pStm, REFIID riid, void *pv, DWORD dwDestContext, void *pvDestCtx, DWORD mshlflags) { // save to the stream T* pT = static_cast(this); HRESULT hr = E_FAIL; hr = pT->Save(pStm, FALSE); return hr; } STDMETHODIMP UnmarshalInterface(IStream *pStm, REFIID riid, void **ppv) { // load from the stream T* pT = static_cast(this); HRESULT hr = pT->Load(pStm); if (FAILED(hr)) return hr; return pT->QueryInterface(riid,ppv); } STDMETHODIMP ReleaseMarshalData(IStream *pStm) { // no-op return S_OK; } STDMETHODIMP DisconnectObject(DWORD dwReserved) { return S_OK; } };