/****************************************************************************** Copyright (c) 2000 Microsoft Corporation Module Name: main.cpp Abstract: This file contains the implementation of the WinMain function for HelpSvc. Revision History: Davide Massarenti (Dmassare) 03/14/2000 created ******************************************************************************/ #include "stdafx.h" #include #include #include "msscript.h" #include "HelpServiceTypeLib.h" #include "HelpServiceTypeLib_i.c" #include "HelpCenterTypeLib.h" #include "HelpCenterTypeLib_i.c" BEGIN_OBJECT_MAP(ObjectMap) OBJECT_ENTRY(CLSID_PCHServiceReal, CPCHService ) OBJECT_ENTRY(CLSID_PCHUpdateReal , HCUpdate::Engine ) #ifndef NOJETBLUECOM OBJECT_ENTRY(CLSID_PCHDBSessionReal , JetBlueCOM::Session) #endif END_OBJECT_MAP() //////////////////////////////////////////////////////////////////////////////// static HRESULT PurgeTempFiles() { __HCP_FUNC_ENTRY( "PurgeTempFiles" ); HRESULT hr; MPC::wstring szTempPath( HC_ROOT_HELPSVC_TEMP ); MPC::SubstituteEnvVariables( szTempPath ); MPC::FileSystemObject fso( szTempPath.c_str() ); MPC::FileSystemObject::List fso_lst; MPC::FileSystemObject::IterConst fso_it; // // Inspect the temp directory. // __MPC_EXIT_IF_METHOD_FAILS(hr, fso.CreateDir( true )); // // Delete any subdirectory. // __MPC_EXIT_IF_METHOD_FAILS(hr, fso.EnumerateFolders( fso_lst )); for(fso_it=fso_lst.begin(); fso_it != fso_lst.end(); fso_it++) { __MPC_EXIT_IF_METHOD_FAILS(hr, (*fso_it)->Delete( true, false )); } fso_lst.clear(); // // For each file, if it's not in the database, delete it. // __MPC_EXIT_IF_METHOD_FAILS(hr, fso.EnumerateFiles( fso_lst )); for(fso_it=fso_lst.begin(); fso_it != fso_lst.end(); fso_it++) { __MPC_EXIT_IF_METHOD_FAILS(hr, (*fso_it)->Delete( false, false )); } fso_lst.clear(); hr = S_OK; __HCP_FUNC_CLEANUP; __HCP_FUNC_EXIT(hr); } static HRESULT InitAll() { __HCP_FUNC_ENTRY( "InitAll" ); HRESULT hr; __MPC_EXIT_IF_METHOD_FAILS(hr, MPC::LocalizeInit()); __MPC_EXIT_IF_METHOD_FAILS(hr, JetBlue::SessionPool ::InitializeSystem( )); __MPC_EXIT_IF_METHOD_FAILS(hr, Taxonomy::InstalledInstanceStore::InitializeSystem( )); __MPC_EXIT_IF_METHOD_FAILS(hr, Taxonomy::Cache ::InitializeSystem( )); __MPC_EXIT_IF_METHOD_FAILS(hr, OfflineCache::Root ::InitializeSystem( /*fMaster*/true )); __MPC_EXIT_IF_METHOD_FAILS(hr, CPCHContentStore ::InitializeSystem( /*fMaster*/true )); __MPC_EXIT_IF_METHOD_FAILS(hr, CPCHUserProcess ::InitializeSystem( )); __MPC_EXIT_IF_METHOD_FAILS(hr, CPCHSecurity ::InitializeSystem( )); __MPC_EXIT_IF_METHOD_FAILS(hr, CPCHSystemMonitor ::InitializeSystem( )); __MPC_EXIT_IF_METHOD_FAILS(hr, CSAFReg ::InitializeSystem( )); hr = S_OK; __HCP_FUNC_CLEANUP; __HCP_FUNC_EXIT(hr); } static void CleanAll() { // // Make sure everything is stopped before releasing any object. // if(Taxonomy::InstalledInstanceStore::s_GLOBAL) { Taxonomy::InstalledInstanceStore::s_GLOBAL->Shutdown(); } CSAFReg ::FinalizeSystem(); CPCHSystemMonitor ::FinalizeSystem(); CPCHSecurity ::FinalizeSystem(); CPCHUserProcess ::FinalizeSystem(); CPCHContentStore ::FinalizeSystem(); OfflineCache::Root ::FinalizeSystem(); Taxonomy::Cache ::FinalizeSystem(); Taxonomy::InstalledInstanceStore::FinalizeSystem(); JetBlue::SessionPool ::FinalizeSystem(); } static HRESULT ProcessArguments( int argc , LPCWSTR* argv ) { __HCP_FUNC_ENTRY( "ProcessArguments" ); HRESULT hr; int i; LPCWSTR szSvcHostGroup = NULL; bool fCOM_reg = false; bool fCOM_unreg = false; bool fInstall = false; bool fUninstall = false; bool fCollect = false; bool fRunAsService = true; bool fRun = true; bool fMUI_install = false; bool fMUI_uninstall = false; LPCWSTR MUI_language = NULL; CComBSTR MUI_cabinet; __MPC_EXIT_IF_METHOD_FAILS(hr, InitAll()); for(i=1; i svc; long lLCID = 0; if(MUI_language) { swscanf( MUI_language, L"%lx", &lLCID ); } if(FAILED(hr = ::CoCreateInstance( CLSID_PCHService, NULL, CLSCTX_ALL, IID_IPCHService, (void**)&svc ))) { static WCHAR s_szRunOnceKey[] = L"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\RunOnce"; MPC::RegKey rk; MPC::wstring szName = L"DelayedHelpSvc_"; WCHAR rgBuf[8]; if(fCollect) { szName += L"Collect"; } if(fMUI_install) { StringCchPrintfW( rgBuf, ARRAYSIZE(rgBuf), L"%04x", (int)lLCID ); szName += L"MUI_Install_"; szName += rgBuf; } if(fMUI_uninstall) { StringCchPrintfW( rgBuf, ARRAYSIZE(rgBuf), L"%04x", (int)lLCID ); szName += L"MUI_Uninstall_"; szName += rgBuf; } if(SUCCEEDED(rk.SetRoot( HKEY_LOCAL_MACHINE, KEY_ALL_ACCESS )) && SUCCEEDED(rk.Attach ( s_szRunOnceKey )) && SUCCEEDED(rk.Create ( )) ) { MPC::wstring szCmd = ::GetCommandLineW(); rk.Write( szCmd, szName.c_str() ); } __MPC_SET_ERROR_AND_EXIT(hr, S_OK); } if(fCollect) { __MPC_EXIT_IF_METHOD_FAILS(hr, svc->TriggerScheduledDataCollection( VARIANT_TRUE )); } if(fMUI_install) { __MPC_EXIT_IF_METHOD_FAILS(hr, svc->MUI_Install( lLCID, MUI_cabinet )); } if(fMUI_uninstall) { __MPC_EXIT_IF_METHOD_FAILS(hr, svc->MUI_Uninstall( lLCID )); } } catch(...) { __MPC_SET_ERROR_AND_EXIT(hr, EXCEPTION_NONCONTINUABLE_EXCEPTION); } __MPC_SET_ERROR_AND_EXIT(hr, S_OK); } ////////////////////////////////////////////////////////////////////// if(fCOM_unreg) { _Module.UnregisterServer( szSvcHostGroup ); } if(fCOM_reg) { _Module.RegisterServer( TRUE, (szSvcHostGroup != NULL), szSvcHostGroup ); } if(fInstall) { try { (void)Local_Install(); } catch(...) { __MPC_SET_ERROR_AND_EXIT(hr, EXCEPTION_NONCONTINUABLE_EXCEPTION); } } if(fUninstall) { try { (void)Local_Uninstall(); } catch(...) { __MPC_SET_ERROR_AND_EXIT(hr, EXCEPTION_NONCONTINUABLE_EXCEPTION); } } ////////////////////////////////////////////////////////////////////// if(fRun) { #ifdef DEBUG _Module.ReadDebugSettings(); #endif DEBUG_AppendPerf( DEBUG_PERF_HELPSVC, "Start" ); try { __MPC_EXIT_IF_METHOD_FAILS(hr, PurgeTempFiles()); // // To run properly, we need this privilege. // __MPC_EXIT_IF_METHOD_FAILS(hr, MPC::SecurityDescriptor::SetPrivilege( L"SeSecurityPrivilege" )); __MPC_EXIT_IF_METHOD_FAILS(hr, CPCHSystemMonitor::s_GLOBAL->Startup()); DEBUG_AppendPerf( DEBUG_PERF_HELPSVC, "Started" ); _Module.Start( fRunAsService ? TRUE : FALSE ); } catch(...) { __MPC_SET_ERROR_AND_EXIT(hr, EXCEPTION_NONCONTINUABLE_EXCEPTION); } DEBUG_AppendPerf( DEBUG_PERF_HELPSVC, "Shutdown" ); DEBUG_DumpPerf ( L"%WINDIR%\\TEMP\\HELPSVC_perf_counters.txt" ); } ////////////////////////////////////////////////////////////////////// hr = S_OK; __HCP_FUNC_CLEANUP; CleanAll(); __HCP_FUNC_EXIT(hr); } extern "C" int WINAPI wWinMain( HINSTANCE hInstance , HINSTANCE hPrevInstance, LPWSTR lpCmdLine , int nShowCmd ) { HRESULT hr; int argc; LPCWSTR* argv; if(SUCCEEDED(hr = ::CoInitializeEx( NULL, COINIT_MULTITHREADED ))) // We need to be a multi-threaded application. { if(SUCCEEDED(hr = ::CoInitializeSecurity( NULL , -1 , // We don't care which authentication service we use. NULL , NULL , RPC_C_AUTHN_LEVEL_CONNECT , // We want to identify the callers. RPC_C_IMP_LEVEL_IDENTIFY , NULL , EOAC_DYNAMIC_CLOAKING , // Let's use the thread token for outbound calls. NULL ))) { #ifdef PCH_DEBUG_SETUP { static WCHAR s_szDebugAsyncTrace[] = L"SOFTWARE\\Microsoft\\MosTrace\\CurrentVersion\\DebugAsyncTrace"; MPC::RegKey rkTrace; if(SUCCEEDED(rkTrace.SetRoot( HKEY_LOCAL_MACHINE, KEY_ALL_ACCESS )) && SUCCEEDED(rkTrace.Attach ( s_szDebugAsyncTrace )) && SUCCEEDED(rkTrace.Create ( )) ) { CComVariant vValue; vValue = (long)0x00000000 ; (void)rkTrace.put_Value( vValue, L"AsyncThreadPriority" ); vValue = (long)0x00000001 ; (void)rkTrace.put_Value( vValue, L"OutputTraceType" ); vValue = (long)500*1024*1024; (void)rkTrace.put_Value( vValue, L"MaxTraceFileSize" ); vValue = L"c:\\trace.atf" ; (void)rkTrace.put_Value( vValue, L"TraceFile" ); vValue = (long)0x00000001 ; (void)rkTrace.put_Value( vValue, L"AsyncTraceFlag" ); vValue = (long)0x0000003F ; (void)rkTrace.put_Value( vValue, L"EnabledTraces" ); } } #endif __MPC_TRACE_INIT(); g_NTEvents.Init( L"HELPSVC" ); // // Parse the command line. // if(SUCCEEDED(hr = MPC::CommandLine_Parse( argc, argv ))) { // // Initialize ATL modules. // _Module.Init( ObjectMap, hInstance, HC_HELPSVC_NAME, IDS_HELPSVC_DISPLAYNAME, IDS_HELPSVC_DESCRIPTION ); // // Initialize MPC module. // if(SUCCEEDED(hr = MPC::_MPC_Module.Init())) { // // Process arguments. // hr = ProcessArguments( argc, argv ); MPC::_MPC_Module.Term(); } _Module.Term(); MPC::CommandLine_Free( argc, argv ); } __MPC_TRACE_TERM(); } ::CoUninitialize(); } return FAILED(hr) ? 10 : 0; }