topical media & game development
hush-src-multi-DLL-MultiVMR9.cpp / cpp
//------------------------------------------------------------------------------
// File: MultiVMR9.cpp
//
// Desc: DirectShow sample code - Implementation of DLL Exports.
//
// Copyright (c) Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
include <stdafx.h>
include <resource.h>
include <MultiVMR9.h>
include <stdio.h>
include <tchar.h>
include <Wizard.h>
include <RenderEngine.h>
include <UILayer.h>
include <MixerControl.h>
HINSTANCE g_hInst = NULL;
class CCFMultiVMR9Wizard;
class CCFMultiVMR9RenderEngine;
class CCFMultiVMR9UILayer;
class CCFMultiVMR9MixerControl;
static CCFMultiVMR9Wizard g_WizardFactory;
static CCFMultiVMR9RenderEngine g_RenderEngineFactory;
static CCFMultiVMR9UILayer g_UILayerFactory;
static CCFMultiVMR9MixerControl g_MixerControlFactory;
// the com module's lock count + object count
long g_CountWizard = 0;
long g_CountRenderEngine = 0;
long g_CountUILayer = 0;
long g_CountMixerControl = 0;
// forward declarations
void MultiVMRRegisterClass( const CLSID& clsid, TCHAR *achClassName, BOOL bRegister);
LONG recursiveDeleteKey(HKEY hKeyParent, TCHAR* achKeyChild);
// DLL Entry Point
BOOL WINAPI DllMain(HINSTANCE hInstance, DWORD dwReason, LPVOID lpReserved)
{
if (DLL_PROCESS_ATTACH == dwReason )
{
g_hInst = hInstance;
}
return(TRUE);
}
//
// stub entry points
//
STDAPI
DllRegisterServer( void )
{
// now go register components; they are in HKEY_CLASSES_ROOT\CLSID{uuid}
MultiVMRRegisterClass( CLSID_MultiVMR9Wizard, TEXT("MultiVMR9 Wizard"), TRUE);
MultiVMRRegisterClass( CLSID_MultiVMR9RenderEngine, TEXT("MultiVMR9 Render Engine"), TRUE);
MultiVMRRegisterClass( CLSID_MultiVMR9UILayer, TEXT("MultiVMR9 UI Layer"), TRUE);
MultiVMRRegisterClass( CLSID_MultiVMR9MixerControl, TEXT("MultiVMR9 Mixer Control"), TRUE);
return S_OK;
}
STDAPI
DllUnregisterServer( void )
{
// now go register components; they are in HKEY_CLASSES_ROOT\CLSID{uuid}
MultiVMRRegisterClass( CLSID_MultiVMR9Wizard, TEXT("MultiVMR9 Wizard"), FALSE);
MultiVMRRegisterClass( CLSID_MultiVMR9RenderEngine, TEXT("MultiVMR9 Render Engine"), FALSE);
MultiVMRRegisterClass( CLSID_MultiVMR9UILayer, TEXT("MultiVMR9 UI Layer"), FALSE);
MultiVMRRegisterClass( CLSID_MultiVMR9MixerControl, TEXT("MultiVMR9 Mixer Control"), FALSE);
return S_OK;
}
STDAPI DllGetClassObject(REFCLSID rclsid, REFIID riid, LPVOID * ppv)
{
if (CLSID_MultiVMR9Wizard == rclsid )
{
return g_WizardFactory.QueryInterface(riid, ppv);
}
else if( CLSID_MultiVMR9RenderEngine == rclsid )
{
return g_RenderEngineFactory.QueryInterface(riid, ppv);
}
else if( CLSID_MultiVMR9UILayer == rclsid )
{
return g_UILayerFactory.QueryInterface(riid, ppv);
}
else if( CLSID_MultiVMR9MixerControl == rclsid )
{
return g_MixerControlFactory.QueryInterface(riid, ppv);
}
else
{
*ppv = NULL;
return CLASS_E_CLASSNOTAVAILABLE;
}
}
STDAPI DllCanUnloadNow(void)
{
HRESULT hr = S_FALSE;
if( 0 == g_CountWizard &&
0 == g_CountRenderEngine &&
0 == g_CountUILayer &&
0 == g_CountMixerControl )
{
hr = S_OK;
}
return hr;
}
//
// Add entry to the registry about CLSID object
//
void MultiVMRRegisterClass(
const CLSID& clsid,
TCHAR *achClassName,
BOOL bRegister)
{
HRESULT hr = S_OK;
TCHAR achModule[MAX_PATH];
WCHAR wcModule[MAX_PATH];
WCHAR wcKey[MAX_PATH];
TCHAR achKey[MAX_PATH];
TCHAR achThreadingModel[] = TEXT("Both");
long err = 0;
LPOLESTR wcCLSID = NULL;
HKEY hKey = NULL;
HKEY hSubKey = NULL;
GetModuleFileName( g_hInst, achModule, sizeof(achModule) );
ifdef UNICODE
wcscpy( wcModule, achModule );
else
MultiByteToWideChar(CP_ACP, 0, achModule, -1, wcModule, MAX_PATH);
endif
hr = StringFromCLSID(clsid, &wcCLSID);
wcscpy( wcKey, L"CLSID\\");
wcscat( wcKey, wcCLSID);
ifdef UNICODE
_tcscpy( achKey, wcKey);
else
WideCharToMultiByte(CP_ACP, 0, wcKey, -1, achKey, MAX_PATH, 0, 0);
endif
// first, delete wcKey if it exists
err = recursiveDeleteKey( HKEY_CLASSES_ROOT, achKey);
if( bRegister )
{
// create new key
err = RegCreateKeyEx( HKEY_CLASSES_ROOT,
achKey,
NULL,
NULL,
REG_OPTION_NON_VOLATILE,
KEY_ALL_ACCESS,
NULL,
&hKey,
NULL);
if (ERROR_SUCCESS == err)
{
err = RegSetValueEx( hKey, NULL, 0, REG_SZ,(BYTE *)achClassName,
sizeof(TCHAR) * ( _tcslen(achClassName)+1));
err = RegCreateKeyEx( hKey,
TEXT("InprocServer32"),
NULL,
NULL,
REG_OPTION_NON_VOLATILE,
KEY_ALL_ACCESS,
NULL,
&hSubKey,
NULL);
if( ERROR_SUCCESS == err)
{
err = RegSetValueEx( hSubKey, NULL, 0, REG_SZ,(BYTE *)achModule,
sizeof(TCHAR) * ( _tcslen(achModule)+1));
err = RegSetValueEx( hSubKey, TEXT("ThreadingModel"), 0, REG_SZ,(BYTE *)achThreadingModel,
sizeof(TCHAR) * ( _tcslen(achThreadingModel)+1));
RegCloseKey( hSubKey );
}
RegCloseKey( hKey );
}
}
CoTaskMemFree(wcCLSID);
}
//
// Delete a key and all of its descendents.
//
LONG recursiveDeleteKey(HKEY hKeyParent, // Parent of key to delete
TCHAR* achKeyChild) // Key to delete
{
// Open the child.
HKEY hKeyChild;
LONG lRes = RegOpenKeyEx(hKeyParent, achKeyChild, 0,
KEY_ALL_ACCESS, &hKeyChild);
if (lRes != ERROR_SUCCESS)
{
return lRes;
}
// Enumerate all of the decendents of this child.
FILETIME time;
TCHAR achBuffer[256];
DWORD dwSize = 256;
while (RegEnumKeyEx(hKeyChild, 0, achBuffer, &dwSize, NULL,
NULL, NULL, &time) == ERROR_SUCCESS)
{
// Delete the decendents of this child.
lRes = recursiveDeleteKey(hKeyChild, achBuffer);
if (lRes != ERROR_SUCCESS)
{
// Cleanup before exiting.
RegCloseKey(hKeyChild);
return lRes;
}
dwSize = 256;
}
// Close the child.
RegCloseKey(hKeyChild);
// Delete this child.
return RegDeleteKey(hKeyParent, achKeyChild);
}
ifdef _DEBUG
void DbgMsg( char* szMessage, ... )
{
char szFullMessage[MAX_PATH];
char szFormatMessage[MAX_PATH];
// format message
va_list ap;
va_start(ap, szMessage);
_vsnprintf( szFormatMessage, MAX_PATH, szMessage, ap);
va_end(ap);
strncat( szFormatMessage, "\n", MAX_PATH);
strcpy( szFullMessage, "~*~*~*~*~*~ ");
strcat( szFullMessage, szFormatMessage );
OutputDebugStringA( szFullMessage );
}
else
void DbgMsg( char* szMessage, ... ){;}
endif
(C) Æliens
20/2/2008
You may not copy or print any of this material without explicit permission of the author or the publisher.
In case of other copyright issues, contact the author.