winamp/Src/Plugins/Input/in_dshow/base/dllsetup.cpp
2024-09-24 14:54:57 +02:00

695 lines
18 KiB
C++

//------------------------------------------------------------------------------
// File: DllSetup.cpp
//
// Desc: DirectShow base classes.
//
// Copyright (c) 1992-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#include <streams.h>
#include <strsafe.h>
#include "combase.h"
//---------------------------------------------------------------------------
// defines
#define MAX_KEY_LEN 260
//---------------------------------------------------------------------------
// externally defined functions/variable
//extern int g_cTemplates;
//extern CFactoryTemplate g_Templates[];
//---------------------------------------------------------------------------
//
// EliminateSubKey
//
// Try to enumerate all keys under this one.
// if we find anything, delete it completely.
// Otherwise just delete it.
//
// note - this was pinched/duplicated from
// Filgraph\Mapper.cpp - so should it be in
// a lib somewhere?
//
//---------------------------------------------------------------------------
STDAPI
EliminateSubKey( HKEY hkey, LPCTSTR strSubKey )
{
HKEY hk;
if (0 == lstrlen(strSubKey) ) {
// defensive approach
return E_FAIL;
}
LONG lreturn = RegOpenKeyEx( hkey
, strSubKey
, 0
, MAXIMUM_ALLOWED
, &hk );
ASSERT( lreturn == ERROR_SUCCESS
|| lreturn == ERROR_FILE_NOT_FOUND
|| lreturn == ERROR_INVALID_HANDLE );
if( ERROR_SUCCESS == lreturn )
{
// Keep on enumerating the first (zero-th)
// key and deleting that
for( ; ; )
{
TCHAR Buffer[MAX_KEY_LEN];
DWORD dw = MAX_KEY_LEN;
FILETIME ft;
lreturn = RegEnumKeyEx( hk
, 0
, Buffer
, &dw
, NULL
, NULL
, NULL
, &ft);
ASSERT( lreturn == ERROR_SUCCESS
|| lreturn == ERROR_NO_MORE_ITEMS );
if( ERROR_SUCCESS == lreturn )
{
EliminateSubKey(hk, Buffer);
}
else
{
break;
}
}
RegCloseKey(hk);
RegDeleteKey(hkey, strSubKey);
}
return NOERROR;
}
//---------------------------------------------------------------------------
//
// AMovieSetupRegisterServer()
//
// registers specfied file "szFileName" as server for
// CLSID "clsServer". A description is also required.
// The ThreadingModel and ServerType are optional, as
// they default to InprocServer32 (i.e. dll) and Both.
//
//---------------------------------------------------------------------------
STDAPI
AMovieSetupRegisterServer( CLSID clsServer
, LPCWSTR szDescription
, LPCWSTR szFileName
, LPCWSTR szThreadingModel = L"Both"
, LPCWSTR szServerType = L"InprocServer32" )
{
// temp buffer
//
TCHAR achTemp[MAX_PATH];
// convert CLSID uuid to string and write
// out subkey as string - CLSID\{}
//
OLECHAR szCLSID[CHARS_IN_GUID];
HRESULT hr = StringFromGUID2( clsServer
, szCLSID
, CHARS_IN_GUID );
ASSERT( SUCCEEDED(hr) );
// create key
//
HKEY hkey;
(void)StringCchPrintf( achTemp, NUMELMS(achTemp), TEXT("CLSID\\%ls"), szCLSID );
LONG lreturn = RegCreateKey( HKEY_CLASSES_ROOT
, (LPCTSTR)achTemp
, &hkey );
if( ERROR_SUCCESS != lreturn )
{
return AmHresultFromWin32(lreturn);
}
// set description string
//
(void)StringCchPrintf( achTemp, NUMELMS(achTemp), TEXT("%ls"), szDescription );
lreturn = RegSetValue( hkey
, (LPCTSTR)NULL
, REG_SZ
, achTemp
, sizeof(achTemp) );
if( ERROR_SUCCESS != lreturn )
{
RegCloseKey( hkey );
return AmHresultFromWin32(lreturn);
}
// create CLSID\\{"CLSID"}\\"ServerType" key,
// using key to CLSID\\{"CLSID"} passed back by
// last call to RegCreateKey().
//
HKEY hsubkey;
(void)StringCchPrintf( achTemp, NUMELMS(achTemp), TEXT("%ls"), szServerType );
lreturn = RegCreateKey( hkey
, achTemp
, &hsubkey );
if( ERROR_SUCCESS != lreturn )
{
RegCloseKey( hkey );
return AmHresultFromWin32(lreturn);
}
// set Server string
//
(void)StringCchPrintf( achTemp, NUMELMS(achTemp), TEXT("%ls"), szFileName );
lreturn = RegSetValue( hsubkey
, (LPCTSTR)NULL
, REG_SZ
, (LPCTSTR)achTemp
, sizeof(TCHAR) * (lstrlen(achTemp)+1) );
if( ERROR_SUCCESS != lreturn )
{
RegCloseKey( hkey );
RegCloseKey( hsubkey );
return AmHresultFromWin32(lreturn);
}
(void)StringCchPrintf( achTemp, NUMELMS(achTemp), TEXT("%ls"), szThreadingModel );
lreturn = RegSetValueEx( hsubkey
, TEXT("ThreadingModel")
, 0L
, REG_SZ
, (CONST BYTE *)achTemp
, sizeof(TCHAR) * (lstrlen(achTemp)+1) );
// close hkeys
//
RegCloseKey( hkey );
RegCloseKey( hsubkey );
// and return
//
return HRESULT_FROM_WIN32(lreturn);
}
//---------------------------------------------------------------------------
//
// AMovieSetupUnregisterServer()
//
// default ActiveMovie dll setup function
// - to use must be called from an exported
// function named DllRegisterServer()
//
//---------------------------------------------------------------------------
STDAPI
AMovieSetupUnregisterServer( CLSID clsServer )
{
// convert CLSID uuid to string and write
// out subkey CLSID\{}
//
OLECHAR szCLSID[CHARS_IN_GUID];
HRESULT hr = StringFromGUID2( clsServer
, szCLSID
, CHARS_IN_GUID );
ASSERT( SUCCEEDED(hr) );
TCHAR achBuffer[MAX_KEY_LEN];
(void)StringCchPrintf( achBuffer, NUMELMS(achBuffer), TEXT("CLSID\\%ls"), szCLSID );
// delete subkey
//
hr = EliminateSubKey( HKEY_CLASSES_ROOT, achBuffer );
ASSERT( SUCCEEDED(hr) );
// return
//
return NOERROR;
}
//---------------------------------------------------------------------------
//
// AMovieSetupRegisterFilter through IFilterMapper2
//
//---------------------------------------------------------------------------
STDAPI
AMovieSetupRegisterFilter2( const AMOVIESETUP_FILTER * const psetupdata
, IFilterMapper2 * pIFM2
, BOOL bRegister )
{
DbgLog((LOG_TRACE, 3, TEXT("= AMovieSetupRegisterFilter")));
// check we've got data
//
if( NULL == psetupdata ) return S_FALSE;
// unregister filter
// (as pins are subkeys of filter's CLSID key
// they do not need to be removed separately).
//
DbgLog((LOG_TRACE, 3, TEXT("= = unregister filter")));
HRESULT hr = pIFM2->UnregisterFilter(
0, // default category
0, // default instance name
*psetupdata->clsID );
if( bRegister )
{
REGFILTER2 rf2;
rf2.dwVersion = 1;
rf2.dwMerit = psetupdata->dwMerit;
rf2.cPins = psetupdata->nPins;
rf2.rgPins = psetupdata->lpPin;
// register filter
//
DbgLog((LOG_TRACE, 3, TEXT("= = register filter")));
hr = pIFM2->RegisterFilter(*psetupdata->clsID
, psetupdata->strName
, 0 // moniker
, 0 // category
, NULL // instance
, &rf2);
}
// handle one acceptable "error" - that
// of filter not being registered!
// (couldn't find a suitable #define'd
// name for the error!)
//
if( 0x80070002 == hr)
return NOERROR;
else
return hr;
}
//---------------------------------------------------------------------------
//
// RegisterAllServers()
//
//---------------------------------------------------------------------------
/*
STDAPI
RegisterAllServers( LPCWSTR szFileName, BOOL bRegister )
{
HRESULT hr = NOERROR;
for( int i = 0; i < g_cTemplates; i++ )
{
// get i'th template
//
const CFactoryTemplate *pT = &g_Templates[i];
DbgLog((LOG_TRACE, 2, TEXT("- - register %ls"),
(LPCWSTR)pT->m_Name ));
// register CLSID and InprocServer32
//
if( bRegister )
{
hr = AMovieSetupRegisterServer( *(pT->m_ClsID)
, (LPCWSTR)pT->m_Name
, szFileName );
}
else
{
hr = AMovieSetupUnregisterServer( *(pT->m_ClsID) );
}
// check final error for this pass
// and break loop if we failed
//
if( FAILED(hr) )
break;
}
return hr;
}
*/
//---------------------------------------------------------------------------
//
// AMovieDllRegisterServer2()
//
// default ActiveMovie dll setup function
// - to use must be called from an exported
// function named DllRegisterServer()
//
// this function is table driven using the
// static members of the CFactoryTemplate
// class defined in the dll.
//
// it registers the Dll as the InprocServer32
// and then calls the IAMovieSetup.Register
// method.
//
//---------------------------------------------------------------------------
//STDAPI
//AMovieDllRegisterServer2( BOOL bRegister )
//{
// HRESULT hr = NOERROR;
//
// DbgLog((LOG_TRACE, 2, TEXT("AMovieDllRegisterServer2()")));
//
// // get file name (where g_hInst is the
// // instance handle of the filter dll)
// //
// WCHAR achFileName[MAX_PATH];
//
// // WIN95 doesn't support GetModuleFileNameW
// //
// {
// char achTemp[MAX_PATH];
//
// DbgLog((LOG_TRACE, 2, TEXT("- get module file name")));
//
// // g_hInst handle is set in our dll entry point. Make sure
// // DllEntryPoint in dllentry.cpp is called
// ASSERT(g_hInst != 0);
//
// if( 0 == GetModuleFileNameA( g_hInst
// , achTemp
// , sizeof(achTemp) ) )
// {
// // we've failed!
// DWORD dwerr = GetLastError();
// return AmHresultFromWin32(dwerr);
// }
//
// MultiByteToWideChar( CP_ACP
// , 0L
// , achTemp
// , lstrlenA(achTemp) + 1
// , achFileName
// , NUMELMS(achFileName) );
// }
//
// //
// // first registering, register all OLE servers
// //
// if( bRegister )
// {
// DbgLog((LOG_TRACE, 2, TEXT("- register OLE Servers")));
// hr = RegisterAllServers( achFileName, TRUE );
// }
//
// //
// // next, register/unregister all filters
// //
//
// if( SUCCEEDED(hr) )
// {
// // init is ref counted so call just in case
// // we're being called cold.
// //
// DbgLog((LOG_TRACE, 2, TEXT("- CoInitialize")));
// hr = CoInitialize( (LPVOID)NULL );
// ASSERT( SUCCEEDED(hr) );
//
// // get hold of IFilterMapper2
// //
// DbgLog((LOG_TRACE, 2, TEXT("- obtain IFilterMapper2")));
// IFilterMapper2 *pIFM2 = 0;
// IFilterMapper *pIFM = 0;
// hr = CoCreateInstance( CLSID_FilterMapper2
// , NULL
// , CLSCTX_INPROC_SERVER
// , IID_IFilterMapper2
// , (void **)&pIFM2 );
// if(FAILED(hr))
// {
// DbgLog((LOG_TRACE, 2, TEXT("- trying IFilterMapper instead")));
//
// hr = CoCreateInstance(
// CLSID_FilterMapper,
// NULL,
// CLSCTX_INPROC_SERVER,
// IID_IFilterMapper,
// (void **)&pIFM);
// }
// if( SUCCEEDED(hr) )
// {
// // scan through array of CFactoryTemplates
// // registering servers and filters.
// //
// DbgLog((LOG_TRACE, 2, TEXT("- register Filters")));
// for( int i = 0; i < g_cTemplates; i++ )
// {
// // get i'th template
// //
// const CFactoryTemplate *pT = &g_Templates[i];
//
// if( NULL != pT->m_pAMovieSetup_Filter )
// {
// DbgLog((LOG_TRACE, 2, TEXT("- - register %ls"), (LPCWSTR)pT->m_Name ));
//
// if(pIFM2)
// {
// hr = AMovieSetupRegisterFilter2( pT->m_pAMovieSetup_Filter, pIFM2, bRegister );
// }
// else
// {
// hr = AMovieSetupRegisterFilter( pT->m_pAMovieSetup_Filter, pIFM, bRegister );
// }
// }
//
// // check final error for this pass
// // and break loop if we failed
// //
// if( FAILED(hr) )
// break;
// }
//
// // release interface
// //
// if(pIFM2)
// pIFM2->Release();
// else
// pIFM->Release();
//
// }
//
// // and clear up
// //
// CoFreeUnusedLibraries();
// CoUninitialize();
// }
//
// //
// // if unregistering, unregister all OLE servers
// //
// if( SUCCEEDED(hr) && !bRegister )
// {
// DbgLog((LOG_TRACE, 2, TEXT("- register OLE Servers")));
// hr = RegisterAllServers( achFileName, FALSE );
// }
//
// DbgLog((LOG_TRACE, 2, TEXT("- return %0x"), hr));
// return hr;
//}
//---------------------------------------------------------------------------
//
// AMovieDllRegisterServer()
//
// default ActiveMovie dll setup function
// - to use must be called from an exported
// function named DllRegisterServer()
//
// this function is table driven using the
// static members of the CFactoryTemplate
// class defined in the dll.
//
// it registers the Dll as the InprocServer32
// and then calls the IAMovieSetup.Register
// method.
//
//---------------------------------------------------------------------------
//STDAPI
//AMovieDllRegisterServer( void )
//{
// HRESULT hr = NOERROR;
//
// // get file name (where g_hInst is the
// // instance handle of the filter dll)
// //
// WCHAR achFileName[MAX_PATH];
//
// {
// // WIN95 doesn't support GetModuleFileNameW
// //
// char achTemp[MAX_PATH];
//
// if( 0 == GetModuleFileNameA( g_hInst
// , achTemp
// , sizeof(achTemp) ) )
// {
// // we've failed!
// DWORD dwerr = GetLastError();
// return AmHresultFromWin32(dwerr);
// }
//
// MultiByteToWideChar( CP_ACP
// , 0L
// , achTemp
// , lstrlenA(achTemp) + 1
// , achFileName
// , NUMELMS(achFileName) );
// }
//
// // scan through array of CFactoryTemplates
// // registering servers and filters.
// //
// for( int i = 0; i < g_cTemplates; i++ )
// {
// // get i'th template
// //
// const CFactoryTemplate *pT = &g_Templates[i];
//
// // register CLSID and InprocServer32
// //
// hr = AMovieSetupRegisterServer( *(pT->m_ClsID)
// , (LPCWSTR)pT->m_Name
// , achFileName );
//
// // instantiate all servers and get hold of
// // IAMovieSetup, if implemented, and call
// // IAMovieSetup.Register() method
// //
// if( SUCCEEDED(hr) && (NULL != pT->m_lpfnNew) )
// {
// // instantiate object
// //
// PAMOVIESETUP psetup;
// hr = CoCreateInstance( *(pT->m_ClsID)
// , 0
// , CLSCTX_INPROC_SERVER
// , IID_IAMovieSetup
// , reinterpret_cast<void**>(&psetup) );
// if( SUCCEEDED(hr) )
// {
// hr = psetup->Unregister();
// if( SUCCEEDED(hr) )
// hr = psetup->Register();
// psetup->Release();
// }
// else
// {
// if( (E_NOINTERFACE == hr )
// || (VFW_E_NEED_OWNER == hr ) )
// hr = NOERROR;
// }
// }
//
// // check final error for this pass
// // and break loop if we failed
// //
// if( FAILED(hr) )
// break;
//
// } // end-for
//
// return hr;
//}
//---------------------------------------------------------------------------
//
// AMovieDllUnregisterServer()
//
// default ActiveMovie dll uninstall function
// - to use must be called from an exported
// function named DllRegisterServer()
//
// this function is table driven using the
// static members of the CFactoryTemplate
// class defined in the dll.
//
// it calls the IAMovieSetup.Unregister
// method and then unregisters the Dll
// as the InprocServer32
//
//---------------------------------------------------------------------------
//STDAPI
//AMovieDllUnregisterServer()
//{
// // initialize return code
// //
// HRESULT hr = NOERROR;
//
// // scan through CFactory template and unregister
// // all OLE servers and filters.
// //
// for( int i = g_cTemplates; i--; )
// {
// // get i'th template
// //
// const CFactoryTemplate *pT = &g_Templates[i];
//
// // check method exists
// //
// if( NULL != pT->m_lpfnNew )
// {
// // instantiate object
// //
// PAMOVIESETUP psetup;
// hr = CoCreateInstance( *(pT->m_ClsID)
// , 0
// , CLSCTX_INPROC_SERVER
// , IID_IAMovieSetup
// , reinterpret_cast<void**>(&psetup) );
// if( SUCCEEDED(hr) )
// {
// hr = psetup->Unregister();
// psetup->Release();
// }
// else
// {
// if( (E_NOINTERFACE == hr )
// || (VFW_E_NEED_OWNER == hr ) )
// hr = NOERROR;
// }
// }
//
// // unregister CLSID and InprocServer32
// //
// if( SUCCEEDED(hr) )
// {
// hr = AMovieSetupUnregisterServer( *(pT->m_ClsID) );
// }
//
// // check final error for this pass
// // and break loop if we failed
// //
// if( FAILED(hr) )
// break;
// }
//
// return hr;
//}