mirror of https://github.com/lianthony/NT4.0
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
326 lines
6.0 KiB
326 lines
6.0 KiB
/***
|
|
*
|
|
* Copyright (C) 1993-1994, Microsoft Corporation. All Rights Reserved.
|
|
* Information Contained Herein Is Proprietary and Confidential.
|
|
*
|
|
* File:
|
|
* hello.cpp
|
|
*
|
|
* Purpose:
|
|
* See comment in hello.h
|
|
*
|
|
*****************************************************************************/
|
|
|
|
|
|
#include "common.h"
|
|
#include "resource.h"
|
|
#include "hello.h"
|
|
|
|
|
|
|
|
|
|
|
|
IUnknown FAR*
|
|
CreateDispatchInterface(
|
|
IUnknown FAR* punkController,
|
|
void FAR* pProgInterface)
|
|
{
|
|
HRESULT hresult;
|
|
ITypeLib FAR* ptlib;
|
|
ITypeInfo FAR* ptinfo;
|
|
IUnknown FAR* punkStdDisp;
|
|
|
|
// Load the the hellotlb type library.
|
|
hresult = LoadRegTypeLib(LIBID_HELLOTLB, 1, 0, 0x0409, &ptlib);
|
|
if (hresult != NOERROR) {
|
|
#define TLB_NAME OLESTR("hello.tlb")
|
|
|
|
// if it wasn't registered, try to load it from the path/current directory
|
|
// if this succeeds, it will have registered the type library for us
|
|
// for the next time.
|
|
if((hresult = LoadTypeLib(TLB_NAME, &ptlib)) != NOERROR)
|
|
return NULL;
|
|
}
|
|
|
|
// Get Dispatch TypeInfo from the type library.
|
|
// Exit if an error occurs.
|
|
hresult = ptlib->GetTypeInfoOfGuid(IID_IHello, &ptinfo);
|
|
if (hresult != NOERROR)
|
|
return NULL;
|
|
|
|
ptlib->Release();
|
|
|
|
// Create a standard dispatch object.
|
|
// Release the pointer to the previously created TypeInfo.
|
|
// Exit if an error occurred.
|
|
hresult = CreateStdDispatch(punkController,
|
|
pProgInterface,
|
|
ptinfo,
|
|
&punkStdDisp);
|
|
ptinfo->Release();
|
|
if (hresult != NOERROR)
|
|
return NULL;
|
|
|
|
|
|
// If execution has reached this point, then no errors occurred.
|
|
return punkStdDisp;
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/*
|
|
* CHello::CHello(void)
|
|
*
|
|
*/
|
|
CHello::CHello()
|
|
{
|
|
m_refs = 1;
|
|
m_disp_interface = NULL;
|
|
m_prog_interface = new CHelloPro;
|
|
m_prog_interface->m_phello = this;
|
|
m_bstrHelloMsg = SysAllocString(OLESTR("Hello, world"));
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/*
|
|
* CHello::~CHello(void)
|
|
*
|
|
*/
|
|
CHello::~CHello()
|
|
{
|
|
SysFreeString(m_bstrHelloMsg);
|
|
delete m_prog_interface;
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/*
|
|
* CHello *CHello::Create(void)
|
|
*
|
|
* Creates a new instance of the CHello object.
|
|
*
|
|
* Returns a pointer to the newly created instance or
|
|
* NULL if the creation fails.
|
|
*
|
|
*/
|
|
CHello FAR*
|
|
CHello::Create()
|
|
{
|
|
CHello FAR* phello;
|
|
IUnknown FAR* punkStdDisp;
|
|
|
|
|
|
// Create an instance of CHello. Exit if an error occurs.
|
|
phello = new FAR CHello();
|
|
if(phello == NULL)
|
|
return NULL;
|
|
|
|
punkStdDisp = CreateDispatchInterface((IUnknown FAR*) phello,
|
|
phello->m_prog_interface);
|
|
if (punkStdDisp == NULL) {
|
|
phello->Release();
|
|
return NULL;
|
|
}
|
|
|
|
|
|
// If execution has reached this point, then no errors have occurred.
|
|
// Save the standard dispatch item and return the new instance.
|
|
phello->m_disp_interface = punkStdDisp;
|
|
return phello;
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/*
|
|
* void CHello::ProcessCommand(WPARAM param)
|
|
*
|
|
* Process a windows WM_COMMAND with the specified parameter.
|
|
*
|
|
*/
|
|
void CHello::ProcessCommand(WPARAM wparam)
|
|
{
|
|
switch(wparam) {
|
|
case IDC_SAYHELLO:
|
|
// The user pressed the "Say Hello" button.
|
|
m_prog_interface->SayHello();
|
|
break;
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
//---------------------------------------------------------------------
|
|
// IUnknown methods
|
|
//---------------------------------------------------------------------
|
|
|
|
|
|
/* CHello::QueryInterface(...)
|
|
*
|
|
* Someone wants to know if CHello support the interface identified
|
|
* by riid. CHello supports IUnknown and we defer to a member
|
|
* (m_disp_interfaceatch) and thus support IDispatch.
|
|
*
|
|
* CHello doesn't support any other interfaces.
|
|
*
|
|
*/
|
|
STDMETHODIMP
|
|
CHello::QueryInterface(REFIID riid, void FAR* FAR* ppv)
|
|
{
|
|
// riid identifies an interface type. Do we support it?
|
|
|
|
if (IsEqualIID(riid, IID_IUnknown))
|
|
// Someone is asking us for our controlling IUnknown.
|
|
// CHello is that IUnknown, so "this" is the answer.
|
|
*ppv = this;
|
|
else if (IsEqualIID(riid, IID_IDispatch) ||
|
|
IsEqualIID(riid, IID_DHello))
|
|
// Someone is asking us for our IDispatch or dispinterface.
|
|
// We simply defer to the standard dispatch interface
|
|
// we created earlier.
|
|
return m_disp_interface->QueryInterface(IID_IDispatch, ppv);
|
|
else if (IsEqualIID(riid, IID_IHello))
|
|
// Someone is asking us for our IHelloPro interface.
|
|
// We simply defer to the standard dispatch interface
|
|
// we created earlier.
|
|
*ppv = &m_prog_interface;
|
|
else {
|
|
// They must have asked for another interface -- something
|
|
// we don't support. Report the error.
|
|
*ppv = NULL;
|
|
return ResultFromScode(E_NOINTERFACE);
|
|
}
|
|
|
|
// If execution reached this point then no error occurred.
|
|
AddRef();
|
|
return NOERROR;
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
STDMETHODIMP_(ULONG)
|
|
CHello::AddRef()
|
|
{
|
|
return ++m_refs;
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
STDMETHODIMP_(ULONG)
|
|
CHello::Release()
|
|
{
|
|
if(--m_refs == 0)
|
|
{
|
|
if(m_disp_interface != NULL)
|
|
m_disp_interface->Release();
|
|
PostQuitMessage(0);
|
|
delete this;
|
|
return 0;
|
|
}
|
|
return m_refs;
|
|
}
|
|
|
|
|
|
|
|
|
|
//---------------------------------------------------------------------
|
|
// The CHello Class Factory
|
|
//---------------------------------------------------------------------
|
|
|
|
|
|
CHelloCF::CHelloCF()
|
|
{
|
|
m_refs = 1;
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
IClassFactory FAR*
|
|
CHelloCF::Create()
|
|
{
|
|
return new FAR CHelloCF();
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
STDMETHODIMP
|
|
CHelloCF::QueryInterface(REFIID riid, void FAR* FAR* ppv)
|
|
{
|
|
if(IsEqualIID(riid, IID_IUnknown) ||
|
|
IsEqualIID(riid, IID_IClassFactory)) {
|
|
AddRef();
|
|
*ppv = this;
|
|
return NOERROR;
|
|
}
|
|
*ppv = NULL;
|
|
return ResultFromScode(E_NOINTERFACE);
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
STDMETHODIMP_(ULONG)
|
|
CHelloCF::AddRef()
|
|
{
|
|
return ++m_refs;
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
STDMETHODIMP_(ULONG)
|
|
CHelloCF::Release()
|
|
{
|
|
if(--m_refs == 0) {
|
|
delete this;
|
|
return 0;
|
|
}
|
|
return m_refs;
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
STDMETHODIMP
|
|
CHelloCF::CreateInstance(
|
|
IUnknown FAR* punkOuter,
|
|
REFIID riid,
|
|
void FAR* FAR* ppv)
|
|
{
|
|
extern CHello FAR* g_phello;
|
|
|
|
|
|
return g_phello->QueryInterface(riid, ppv);
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
STDMETHODIMP
|
|
CHelloCF::LockServer(BOOL fLock)
|
|
{
|
|
return NOERROR;
|
|
}
|