Index: src/ch/ch.cpp
===================================================================
diff -u -N -rbfe720fda9529e7a77b4fb6410b4d4945b69188b -r2457755b4084e3d1c80a8e7c77c9f0996312941b
--- src/ch/ch.cpp	(.../ch.cpp)	(revision bfe720fda9529e7a77b4fb6410b4d4945b69188b)
+++ src/ch/ch.cpp	(.../ch.cpp)	(revision 2457755b4084e3d1c80a8e7c77c9f0996312941b)
@@ -83,11 +83,10 @@
 }
 
 CCopyHandlerApp::CCopyHandlerApp() :
-	m_lfLog(),
-	m_piShellExtControl(NULL)
+	m_piShellExtControl(NULL),
+	m_hMapObject(NULL),
+	m_pMainWindow(NULL)
 {
-	m_pMainWindow=NULL;
-
 	// this is the one-instance application
 	InitProtection();
 }
@@ -124,9 +123,9 @@
 	return ictranslate::CResourceManager::Acquire();
 }
 
-chcore::engine_config& GetConfig()
+chcore::TCoreConfig& GetConfig()
 {
-	return chcore::engine_config::Acquire();
+	return chcore::TCoreConfig::Acquire();
 }
 
 int MsgBox(UINT uiID, UINT nType, UINT nIDHelp)
@@ -210,76 +209,91 @@
 
 BOOL CCopyHandlerApp::InitInstance()
 {
-	// set the exception handler to catch the crash dumps
+	// ================================= Crash handling =======================================
 	SetUnhandledExceptionFilter(&MyUnhandledExceptionFilter);
 
-	HRESULT hResult = CoInitializeEx(NULL, COINIT_MULTITHREADED);
-	if(FAILED(hResult))
-		AfxMessageBox(_T("Cannot initialize COM, the application will now exit."), MB_ICONERROR | MB_OK);
+	// ================================= Configuration ========================================
+	CString strPath;
+	CString strCfgPath;
+	CString strLogPath;
 
-	// InitCommonControlsEx() is required on Windows XP if an application
-	// manifest specifies use of ComCtl32.dll version 6 or later to enable
-	// visual styles.  Otherwise, any window creation will fail.
-	INITCOMMONCONTROLSEX InitCtrls;
-	InitCtrls.dwSize = sizeof(InitCtrls);
-	// Set this to include all the common control classes you want to use
-	// in your application.
-	InitCtrls.dwICC = ICC_WIN95_CLASSES;
-	InitCommonControlsEx(&InitCtrls);
+	// note that the GetProgramDataPath() below should create a directory; ExpandPath() could
+	// depend on the directory to be created earlier
+	if(!GetProgramDataPath(strPath))
+	{
+		AfxMessageBox(_T("Cannot initialize Copy Handler (data path cannot be established)."), MB_ICONERROR | MB_OK);
+		return FALSE;
+	}
 
-	EnableHtmlHelp();
-	//SetHelpMode(afxHTMLHelp);
+	strCfgPath = strPath + _T("\\ch.ini");
 
-	CWinApp::InitInstance();
-
-	m_hMapObject = CreateFileMapping(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, sizeof(CSharedConfigStruct), _T("CHLMFile"));
-	if (m_hMapObject == NULL)
-		return FALSE; 
-	
-	// Get a pointer to the file-mapped shared memory.
-	g_pscsShared=(CSharedConfigStruct*)MapViewOfFile(m_hMapObject, FILE_MAP_READ | FILE_MAP_WRITE, 0, 0, 0);
-	if (g_pscsShared == NULL) 
-		return FALSE; 
-	
-	chcore::engine_config& rConfig = chcore::engine_config::Acquire();
-	ictranslate::CResourceManager& rResManager = ictranslate::CResourceManager::Acquire();
-
-	// load configuration
+	// initialize configuration file
+	chcore::TCoreConfig& rConfig = chcore::TCoreConfig::Acquire();
 	rConfig.set_callback(ConfigPropertyChangedCallback, NULL);
-	CString strPath;
-	// note that the GetProgramDataPath() below should create a directory; ExpandPath() could
-	// depend on the directory to be created earlier
-	if(GetProgramDataPath(strPath))
+
+	// read the configuration
+	try
 	{
-		strPath += _T("\\ch.ini");
-		try
-		{
-			rConfig.read(strPath);
-		}
-		catch(...)
-		{
-		}
+		rConfig.read(strCfgPath);
 	}
+	catch(...)
+	{
+	}
 
 	// set working dir for the engine
-	rConfig.set_base_path(strPath);
+	rConfig.SetBasePath(strPath);
 	// register all properties
 	RegisterProperties(&rConfig);
 
-	// set this process class
-	HANDLE hProcess=GetCurrentProcess();
-	::SetPriorityClass(hProcess, (DWORD)rConfig.get_signed_num(PP_PPROCESSPRIORITYCLASS));
+	// ================================= Logging ========================================
+	// initialize the global log file if it is requested by configuration file
+	strLogPath = strPath +  + _T("\\ch.log");
 
+	chcore::TLogger& rLogger = chcore::TLogger::Acquire();
+	try
+	{
+		rLogger.init(strLogPath, (int_t)rConfig.get_signed_num(PP_LOGMAXSIZE), (int_t)rConfig.get_unsigned_num(PP_LOGLEVEL), false, false);
+		rLogger.Enable(rConfig.get_bool(PP_LOGENABLELOGGING));
+	}
+	catch(...)
+	{
+		BOOST_ASSERT(false);
+	}
+
+	LOG_INFO(_T("============================ Initializing Copy Handler ============================"));
+	LOG_INFO(_T(""));
+
+	// ================================= COM ========================================
+	LOG_INFO(_T("Initializing COM"));
+
+	HRESULT hResult = CoInitializeEx(NULL, COINIT_MULTITHREADED);
+	if(FAILED(hResult))
+	{
+		CString strMsg;
+		strMsg.Format(_T("Cannot initialize COM, the application will now exit (result = 0x%lx)"), hResult);
+
+		LOG_ERROR(strMsg);
+		AfxMessageBox(strMsg, MB_ICONERROR | MB_OK);
+		return FALSE;
+	}
+
+	// ================================= Resource manager ========================================
+	LOG_INFO(_T("Initializing resource manager..."));
+
+	ictranslate::CResourceManager& rResManager = ictranslate::CResourceManager::Acquire();
+
 	// set current language
 	TCHAR szPath[_MAX_PATH];
+
 	rResManager.Init(AfxGetInstanceHandle());
 	rResManager.SetCallback(ResManCallback);
 	rConfig.get_string(PP_PLANGUAGE, szPath, _MAX_PATH);
 	TRACE(_T("Help path=%s\n"), szPath);
-	if (!rResManager.SetLanguage(ExpandPath(szPath)))
+	if(!rResManager.SetLanguage(ExpandPath(szPath)))
 	{
 		TCHAR szData[2048];
 		_sntprintf(szData, 2048, _T("Couldn't find the language file specified in configuration file:\n%s\nPlease correct this path to point the language file to use.\nProgram will now exit."), szPath);
+		LOG_ERROR(szData);
 		AfxMessageBox(szData, MB_ICONSTOP | MB_OK);
 		return FALSE;
 	}
@@ -289,31 +303,47 @@
 	// for dialogs
 	ictranslate::CLanguageDialog::SetResManager(&rResManager);
 
-	// initialize log file
-	rConfig.get_string(PP_LOGPATH, szPath, _MAX_PATH);
-	m_lfLog.init(ExpandPath(szPath), (int_t)rConfig.get_signed_num(PP_LOGMAXLIMIT), icpf::log_file::level_debug, false, false);
+	EnableHtmlHelp();
 
-	// TODO: remove unused properties from configuration
-/*	m_lfLog.EnableLogging(m_cfgManager.GetBoolValue(PP_LOGENABLELOGGING));
-	m_lfLog.SetPreciseLimiting(m_cfgManager.GetBoolValue(PP_LOGPRECISELIMITING));
-	m_lfLog.SetSizeLimit(m_cfgManager.GetBoolValue(PP_LOGLIMITATION), m_cfgManager.GetIntValue(PP_LOGMAXLIMIT));
-	m_lfLog.SetTruncateBufferSize(m_cfgManager.GetIntValue(PP_LOGTRUNCBUFFERSIZE));
-	m_lfLog.Init(ExpandPath(szPath), GetResManager());*/
-
-#ifndef _DEBUG		// for easier writing the program - doesn't collide with std CH
-	// set "run with system" registry settings
-	SetAutorun(rConfig.get_bool(PP_PRELOADAFTERRESTART));
-#endif
-
+	// ================================= Checking for running instances of CH ========================================
 	// check instance - return false if it's the second one
-	if (!IsFirstInstance())
+	LOG_INFO(_T("Checking for other running instances of Copy Handler"));
+	if(!IsFirstInstance())
 	{
+		LOG_WARNING(_T("Other instance of Copy Handler is already running. Exiting."));
 		MsgBox(IDS_ONECOPY_STRING);
 		return FALSE;
 	}
 
+	// ================================= Common controls ========================================
+	LOG_INFO(_T("Initializing GUI common controls"));
+
+	// InitCommonControlsEx() is required on Windows XP if an application
+	// manifest specifies use of ComCtl32.dll version 6 or later to enable
+	// visual styles.  Otherwise, any window creation will fail.
+	INITCOMMONCONTROLSEX InitCtrls;
+	InitCtrls.dwSize = sizeof(InitCtrls);
+	// Set this to include all the common control classes you want to use
+	// in your application.
+	InitCtrls.dwICC = ICC_WIN95_CLASSES;
+	InitCommonControlsEx(&InitCtrls);
+
+	// ================================= Shell extension ========================================
+	LOG_INFO(_T("Initializing shared memory for communication with shell extension"));
+
+	m_hMapObject = CreateFileMapping(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, sizeof(CSharedConfigStruct), _T("CHLMFile"));
+	if (m_hMapObject == NULL)
+		return FALSE; 
+	
+	// Get a pointer to the file-mapped shared memory.
+	g_pscsShared=(CSharedConfigStruct*)MapViewOfFile(m_hMapObject, FILE_MAP_READ | FILE_MAP_WRITE, 0, 0, 0);
+	if (g_pscsShared == NULL) 
+		return FALSE; 
+
+	LOG_INFO(_T("Checking shell extension compatibility"));
+
 	// calculate ch version
-	LONG lCHVersion = PRODUCT_VERSION1 << 24 | PRODUCT_VERSION2 << 16 | PRODUCT_VERSION3 << 8 | PRODUCT_VERSION4;
+	long lCHVersion = PRODUCT_VERSION1 << 24 | PRODUCT_VERSION2 << 16 | PRODUCT_VERSION3 << 8 | PRODUCT_VERSION4;
 
 	// check the version of shell extension
 	LONG lVersion = 0;
@@ -328,6 +358,10 @@
 		hResult = m_piShellExtControl->SetFlags(eShellExt_Enabled, eShellExt_Enabled);
 	if(FAILED(hResult) || lCHVersion != lVersion)
 	{
+		CString strMsg;
+		strMsg.Format(_T("Shell extension has different version (0x%lx) than Copy Handler (0x%lx). Shell extension will be disabled."), lVersion, lCHVersion);
+
+		LOG_WARNING(strMsg);
 		MsgBox(IDS_SHELL_EXTENSION_MISMATCH_STRING);
 
 		if(m_piShellExtControl)
@@ -337,13 +371,30 @@
 	if(bstrVersion)
 		::SysFreeString(bstrVersion);
 
+	// ================================= Initial settings ========================================
+	LOG_INFO(_T("Applying initial settings"));
+
+	// set this process priority class
+	HANDLE hProcess=GetCurrentProcess();
+	::SetPriorityClass(hProcess, (DWORD)rConfig.get_signed_num(PP_PPROCESSPRIORITYCLASS));
+
+#ifndef _DEBUG		// for easier writing the program - doesn't collide with std CH
+	// set "run with system" registry settings
+	SetAutorun(rConfig.get_bool(PP_PRELOADAFTERRESTART));
+#endif
+
+	// ================================= Main window ========================================
+	LOG_INFO(_T("Creating main application window"));
 	// create main window
 	m_pMainWindow=new CMainWnd;
 	if (!((CMainWnd*)m_pMainWindow)->Create())
 		return FALSE;				// will be deleted at destructor
 
 	m_pMainWnd = m_pMainWindow;
+	CWinApp::InitInstance();
 
+	LOG_INFO(_T("Copy Handler initialized successfully"));
+
 	return TRUE;
 }
 
@@ -362,12 +413,37 @@
 void CCopyHandlerApp::OnConfigNotify(uint_t uiPropID)
 {
 	// is this language
-	if(uiPropID == PP_PLANGUAGE)
+	switch(uiPropID)
 	{
-		// update language in resource manager
-		TCHAR szPath[_MAX_PATH];
-		GetConfig().get_string(PP_PLANGUAGE, szPath, _MAX_PATH);
-		GetResManager().SetLanguage(ExpandPath(szPath));
+	case PP_PLANGUAGE:
+		{
+			// update language in resource manager
+			TCHAR szPath[_MAX_PATH];
+			GetConfig().get_string(PP_PLANGUAGE, szPath, _MAX_PATH);
+			GetResManager().SetLanguage(ExpandPath(szPath));
+			break;
+		}
+	case PP_LOGENABLELOGGING:
+		{
+			chcore::TLogger& rLogger = chcore::TLogger::Acquire();
+
+			rLogger.Enable(GetConfig().get_bool(PP_LOGENABLELOGGING));
+			break;
+		}
+	case PP_LOGLEVEL:
+		{
+			chcore::TLogger& rLogger = chcore::TLogger::Acquire();
+
+			rLogger.set_log_level((int_t)GetConfig().get_unsigned_num(PP_LOGLEVEL));
+			break;
+		}
+	case PP_LOGMAXSIZE:
+		{
+			chcore::TLogger& rLogger = chcore::TLogger::Acquire();
+
+			rLogger.set_max_size((int_t)GetConfig().get_signed_num(PP_LOGMAXSIZE));
+			break;
+		}
 	}
 }
 
@@ -381,7 +457,7 @@
 	}
 }
 
-HWND CCopyHandlerApp::HHelp(HWND hwndCaller, LPCTSTR pszFile, UINT uCommand, DWORD dwData)
+HWND CCopyHandlerApp::HHelp(HWND hwndCaller, LPCTSTR pszFile, UINT uCommand, DWORD_PTR dwData)
 {
 	PCTSTR pszPath=NULL;
 	WIN32_FIND_DATA wfd;
@@ -452,12 +528,17 @@
 
 int CCopyHandlerApp::ExitInstance()
 {
+	LOG_INFO(_T("Pre-exit step - releasing shell extension"));
 	if(m_piShellExtControl)
 	{
 		m_piShellExtControl->Release();
 		m_piShellExtControl = NULL;
 	}
+
+	LOG_INFO(_T("Pre-exit step - uninitializing COM"));
 	CoUninitialize();
 
+	LOG_INFO(_T("============================ Leaving Copy Handler ============================"));
+
 	return __super::ExitInstance();
 }