home *** CD-ROM | disk | FTP | other *** search
- /*
- * ANIMAL.CPP
- *
- * Aggregatable Animal Object Implementation, Chapter 2
- *
- * Copyright (c)1993-1995 Microsoft Corporation, All Rights Reserved
- *
- * Kraig Brockschmidt, Microsoft
- * Internet : kraigb@microsoft.com
- * Compuserve: >INTERNET:kraigb@microsoft.com
- */
-
- #include <windows.h>
- #include "reuse.h"
- #include "animal.h"
-
-
- /*
- * CreateAnimal
- *
- * Purpose:
- * Creates an instance of Animal returning a requested interface
- * pointer.
- *
- * Parameters:
- * pUnkOuter IUnknown * holding the outer unknown. Can
- * be NULL.
- * riid REFIID interface requested by the caller.
- * ppv void ** in which to return the interface pointer.
- *
- * Return Value:
- * HRESULT NOERROR if successful, CLASS_E_NOAGREGATION if
- * IUnknown is not requested with non-NULL pUnkOuter,
- * or other error as appropriate.
- */
-
- HRESULT CreateAnimal(IUnknown *pUnkOuter, REFIID riid, void **ppv)
- {
- CAnimal *pObj;
-
- //If aggregation is on, check riid==IID_IUnknown
- if (NULL!=pUnkOuter && riid!=IID_IUnknown)
- return ResultFromScode(CLASS_E_NOAGGREGATION);
-
- pObj=new CAnimal(pUnkOuter);
-
- if (NULL==pObj)
- return E_OUTOFMEMORY;
-
- if (!pObj->Init())
- return E_FAIL;
-
- return pObj->QueryInterface(riid, (PPVOID)ppv);
- }
-
-
-
-
-
- /*
- * CAnimal::CAnimal
- * CAnimal::~CAnimal
- *
- * Constructor Parameters:
- * pUnkOuter IUnknown * holding the outer unknown. Can
- * be NULL.
- */
-
- CAnimal::CAnimal(IUnknown *pUnkOuter)
- {
- m_cRef=0;
- m_pImpIAnimal=NULL;
-
- //No AddRef necessary if non-NULL as we're nested.
- m_pUnkOuter=pUnkOuter;
- return;
- }
-
- CAnimal::~CAnimal(void)
- {
- DeleteInterfaceImp(m_pImpIAnimal);
- return;
- }
-
-
-
- /*
- * CAnimal::Init
- *
- * Purpose:
- * Instantiates the interface implementations for this object.
- *
- * Parameters:
- * None
- *
- * Return Value:
- * BOOL TRUE if initialization succeeds, FALSE otherwise.
- */
-
- BOOL CAnimal::Init(void)
- {
- IUnknown *pUnkOuter=m_pUnkOuter;
-
- //Set up the right unknown for delegation
- if (NULL==pUnkOuter)
- pUnkOuter=this;
-
- m_pImpIAnimal=new CImpIAnimal_A(this, pUnkOuter);
-
- if (NULL==m_pImpIAnimal)
- return FALSE;
-
- return TRUE;
- }
-
-
-
-
-
-
- /*
- * CAnimal::QueryInterface
- * CAnimal::AddRef
- * CAnimal::Release
- *
- * Purpose:
- * Non-delegating IUnknown implementation.
- */
-
- STDMETHODIMP CAnimal::QueryInterface(REFIID riid, PPVOID ppv)
- {
- *ppv=NULL;
-
- if (IID_IUnknown==riid)
- *ppv=this;
-
- if (IID_IAnimal==riid)
- *ppv=m_pImpIAnimal;
-
- if (NULL==*ppv)
- return ResultFromScode(E_NOINTERFACE);
-
- ((LPUNKNOWN)*ppv)->AddRef();
- return NOERROR;
- }
-
-
- DWORD CAnimal::AddRef(void)
- {
- return ++m_cRef;
- }
-
- DWORD CAnimal::Release(void)
- {
- if (0!=--m_cRef)
- return m_cRef;
-
- delete this;
- return 0;
- }
-
-
-
-
- //CImpIAnimal_A interface implementation
-
-
- /*
- * CImpIAnimal_A::CImpIAnimal_A
- * CImpIAnimal_A::~CImpIAnimal_A
- *
- * Constructor Parameters:
- * pObj PCAnimal to the outer object
- * pUnkOuter IUnknown * to which to delegate.
- */
-
- CImpIAnimal_A::CImpIAnimal_A(PCAnimal pObj, IUnknown *pUnkOuter)
- {
- m_cRef=0;
- m_pObj=pObj;
- m_pUnkOuter=pUnkOuter; //No AddRef, we're nested
- return;
- }
-
- CImpIAnimal_A::~CImpIAnimal_A(void)
- {
- return;
- }
-
-
-
- /*
- * CImpIAnimal_A::QueryInterface
- * CImpIAnimal_A::AddRef
- * CImpIAnimal_A::Release
- *
- * IUnknown members that delegate to m_pUnkOuter, whatever it is.
- */
-
- STDMETHODIMP CImpIAnimal_A::QueryInterface(REFIID riid, PPVOID ppv)
- {
- return m_pUnkOuter->QueryInterface(riid, ppv);
- }
-
- DWORD CImpIAnimal_A::AddRef(void)
- {
- ++m_cRef;
- return m_pUnkOuter->AddRef();
- }
-
- DWORD CImpIAnimal_A::Release(void)
- {
- --m_cRef;
- return m_pUnkOuter->Release();
- }
-
-
-
- /*
- * CImpIAnimal_A::Eat
- * CImpIAnimal_A::Sleep
- * CImpIAnimal_A::Procreate
- *
- * Purpose:
- * Empty sample functions, no parameters, return NOERROR
- */
-
- STDMETHODIMP CImpIAnimal_A::Eat(void)
- {
- ODS("Animal's IAnimal::Eat called");
- return NOERROR;
- }
-
- STDMETHODIMP CImpIAnimal_A::Sleep(void)
- {
- ODS("Animal's IAnimal::Sleep called");
- return NOERROR;
- }
-
- STDMETHODIMP CImpIAnimal_A::Procreate(void)
- {
- ODS("Animal's IAnimal::Procreate called");
- return NOERROR;
- }
-