|
|
//
// Copyright 1997 - Microsoft
//
//
// DATAOBJ.CPP - A data object
//
#include "pch.h"
#include "dataobj.h"
DEFINE_MODULE("IMADMUI") DEFINE_THISCLASS("CDsPropDataObj") #define THISCLASS CDsPropDataObj
#define LPTHISCLASS CDsPropDataObj*
//
// CreateInstance( )
//
LPVOID CDsPropDataObj_CreateInstance( HWND hwndParent, IDataObject * pido, GUID * pClassGUID, BOOL fReadOnly, LPWSTR pszObjPath, LPWSTR bstrClass ) { TraceFunc( "CDsPropDataObj_CreateInstance( ... )\n" );
LPTHISCLASS lpcc = new THISCLASS( hwndParent, pido, pClassGUID, fReadOnly); if (!lpcc) RETURN(lpcc);
HRESULT hr = THR( lpcc->Init( pszObjPath, bstrClass ) ); if ( hr ) { delete lpcc; RETURN(NULL); }
RETURN((LPVOID) lpcc); }
//
// Constructor
//
THISCLASS::THISCLASS( HWND hwndParent, IDataObject * pido, GUID * pClassGUID, BOOL fReadOnly) : m_fReadOnly(fReadOnly), m_pwszObjName(NULL), m_pwszObjClass(NULL), m_hwnd(hwndParent), m_pPage(pido), m_ClassGUID(*pClassGUID), _cRef(0) { TraceClsFunc( "CDsPropDataObj( )\n" );
if (m_pPage) { m_pPage->AddRef(); }
TraceFuncExit( ); }
//
// Destructor
//
THISCLASS::~THISCLASS(void) { TraceClsFunc( "~CDsPropDataObj( )\n" ); if (m_pPage) { m_pPage->Release(); }
if (m_pwszObjName) { TraceFree(m_pwszObjName); }
if (m_pwszObjClass) { TraceFree(m_pwszObjClass); }
TraceFuncExit( ); }
//
// Init( )
//
HRESULT THISCLASS::Init( LPWSTR pwszObjName, LPWSTR pwszClass ) { TraceClsFunc( "Init( ... )\n" );
HRESULT hr = S_OK;
// IUnknown stuff
BEGIN_QITABLE_IMP( CDsPropDataObj, IDataObject ); QITABLE_IMP( IDataObject ); END_QITABLE_IMP( CDsPropDataObj ); Assert( _cRef == 0); AddRef( );
if (!pwszObjName || *pwszObjName == L'\0') { HRETURN(E_INVALIDARG); } if (!pwszClass || *pwszClass == L'\0') { HRETURN(E_INVALIDARG); }
m_pwszObjName = (LPWSTR) TraceStrDup( pwszObjName ); if ( !m_pwszObjName ) { hr = THR(E_OUTOFMEMORY); goto Error; }
m_pwszObjClass = (LPWSTR) TraceStrDup( pwszClass ); if ( !m_pwszObjClass ) { hr = THR(E_OUTOFMEMORY); goto Error; }
Cleanup: HRETURN(S_OK);
Error: if ( m_pwszObjName ) { TraceFree( m_pwszObjName ); m_pwszObjName = NULL; }
if ( m_pwszObjClass ) { TraceFree( m_pwszObjClass ); m_pwszObjClass = NULL; }
switch (hr) { case S_OK: break; default: MessageBoxFromHResult( m_hwnd, IDC_ERROR_CREATINGACCOUNT_TITLE, hr ); break; }
goto Cleanup; }
// ************************************************************************
//
// IUnknown
//
// ************************************************************************
//
// QueryInterface()
//
STDMETHODIMP THISCLASS::QueryInterface( REFIID riid, LPVOID *ppv ) { TraceClsFunc( "" );
HRESULT hr = ::QueryInterface( this, _QITable, riid, ppv );
QIRETURN( hr, riid ); }
//
// AddRef()
//
STDMETHODIMP_(ULONG) THISCLASS::AddRef( void ) { TraceClsFunc( "[IUnknown] AddRef( )\n" );
InterlockIncrement( _cRef );
RETURN(_cRef); }
//
// Release()
//
STDMETHODIMP_(ULONG) THISCLASS::Release( void ) { TraceClsFunc( "[IUnknown] Release( )\n" ); InterlockDecrement( _cRef );
if ( _cRef ) RETURN(_cRef);
TraceDo( delete this );
RETURN(0); }
// ************************************************************************
//
// IDataObject
//
// ************************************************************************
//
// GetData( )
//
STDMETHODIMP THISCLASS::GetData( FORMATETC * pFormatEtc, STGMEDIUM * pMedium) { TraceClsFunc( "[IDataObject] GetData( ... )\n" ); if (IsBadWritePtr(pMedium, sizeof(STGMEDIUM))) { HRETURN(E_INVALIDARG); } if (!(pFormatEtc->tymed & TYMED_HGLOBAL)) { HRETURN(DV_E_TYMED); }
HRESULT hr = S_OK;
if (pFormatEtc->cfFormat == g_cfDsObjectNames) { // return the object name and class.
//
INT cbPath = sizeof(WCHAR) * (wcslen(m_pwszObjName) + 1); INT cbClass = sizeof(WCHAR) * (wcslen(m_pwszObjClass) + 1); INT cbStruct = sizeof(DSOBJECTNAMES);
LPDSOBJECTNAMES pDSObj;
pDSObj = (LPDSOBJECTNAMES)GlobalAlloc(GMEM_FIXED | GMEM_ZEROINIT, cbStruct + cbPath + cbClass); if (pDSObj == NULL) { hr = THR(STG_E_MEDIUMFULL); goto Error; }
pDSObj->clsidNamespace = CLSID_MicrosoftDS; pDSObj->cItems = 1; pDSObj->aObjects[0].offsetName = cbStruct; pDSObj->aObjects[0].offsetClass = cbStruct + cbPath; if (m_fReadOnly) { pDSObj->aObjects[0].dwFlags = DSOBJECT_READONLYPAGES; }
wcscpy((PWSTR)((BYTE *)pDSObj + cbStruct), m_pwszObjName); wcscpy((PWSTR)((BYTE *)pDSObj + cbStruct + cbPath), m_pwszObjClass);
pMedium->hGlobal = (HGLOBAL)pDSObj; } else if (pFormatEtc->cfFormat == g_cfDsPropCfg) { // return the property sheet notification info. In this case, it is
// the invokding sheet's hwnd.
//
PPROPSHEETCFG pSheetCfg;
pSheetCfg = (PPROPSHEETCFG)GlobalAlloc(GMEM_FIXED | GMEM_ZEROINIT, sizeof(PROPSHEETCFG)); if (pSheetCfg == NULL) { hr = THR(STG_E_MEDIUMFULL); goto Error; }
ZeroMemory(pSheetCfg, sizeof(PROPSHEETCFG));
pSheetCfg->hwndParentSheet = m_hwnd;
pMedium->hGlobal = (HGLOBAL)pSheetCfg; } else { // Pass call on to "parent" object's data obj.
if (m_pPage ) { hr = m_pPage->GetData( pFormatEtc, pMedium ); #ifdef DEBUG
if (hr != DV_E_FORMATETC ) THR(hr); #endif
goto Error; // not really, but we don't want to clean up
} else { hr = THR(E_FAIL); goto Error; } }
pMedium->tymed = TYMED_HGLOBAL; pMedium->pUnkForRelease = NULL;
Error: HRETURN(hr); }
//
// GetDataHere( )
//
STDMETHODIMP THISCLASS::GetDataHere( LPFORMATETC pFormatEtc, LPSTGMEDIUM pMedium) { TraceClsFunc( "[IDataObject] GetDataHere( ... )\n" ); HRESULT hr;
if (IsBadWritePtr(pMedium, sizeof(STGMEDIUM))) { HRETURN(E_INVALIDARG); }
if (pFormatEtc->cfFormat == g_cfMMCGetNodeType) { if (!(pFormatEtc->tymed & TYMED_HGLOBAL)) { hr = THR(DV_E_TYMED); goto Error; } LPSTREAM lpStream; ULONG written;
// Create the stream on the hGlobal passed in.
//
hr = CreateStreamOnHGlobal(pMedium->hGlobal, FALSE, &lpStream); if (hr) goto Error;
hr = lpStream->Write(&m_ClassGUID, sizeof(m_ClassGUID), &written);
// Because we told CreateStreamOnHGlobal with 'FALSE', only the
// stream is released here.
lpStream->Release(); } else if (m_pPage ) { // Pass call on to "parent" object's data obj.
hr = THR( m_pPage->GetDataHere( pFormatEtc, pMedium ) ); } else { hr = THR(E_FAIL); }
Cleanup: HRETURN(hr);
Error: goto Cleanup; }
//
// EnumFormatEtc( )
//
STDMETHODIMP THISCLASS::EnumFormatEtc( DWORD dwDirection, LPENUMFORMATETC * ppEnumFormatEtc) { TraceClsFunc( "[IDataObject] EnumFormatEtc( ... )\n" ); //
// Pass call on to "parent" object's data obj.
//
if (m_pPage ) { HRETURN(m_pPage->EnumFormatEtc(dwDirection, ppEnumFormatEtc)); } else { HRETURN(E_FAIL); } }
|