// ////////////////////////////////////////////////////////////////////// LRESULT CALLBACK MessengerPlusGlobalHook(int nCode, WPARAM wParam, LPARAM lParam) { if(nCode == HCBT_CREATEWND && !GetParent((HWND)wParam) && !g_bInitialized && !g_bStopHooking) //Top Most windows only { TCHAR szClass[256]; szClass[0] = '\0'; try { //Get the class name of this window HWND hwnd = (HWND)wParam; GetClassName(hwnd, szClass, 255); //Main Messenger window if(_tcscmp(szClass, CMainMsgWnd::m_sClassName4) == 0 || _tcscmp(szClass, CMainMsgWnd::m_sClassName5) == 0) { try { if(!g_wndMainMsg || !g_wndMainMsg->IsWindowHooked()) { //Initialize and check if the window is really what we expect TRACE("QuickInitialize will be called from main window hook"); QuickInitialize(); if(CPreferences::GetMPHookState() > 0) Initialize(); else { if(g_mpWnd) g_mpWnd->StartGlobalTimer(); } if(g_bInitialized || CPreferences::GetMPHookState() <= 0) { //Check again... Initialize() can provoke a chain reaction if(!g_wndMainMsg || !g_wndMainMsg->IsWindowHooked()) { #ifdef _DEBUG if(((CPreferences::GetMessengerVersion() < 5 || CPreferences::IsWindowsMessenger()) && _tcscmp(szClass, CMainMsgWnd::m_sClassName5) == 0) || (CPreferences::GetMessengerVersion() >= 5 && _tcscmp(szClass, CMainMsgWnd::m_sClassName4) == 0)) { TRACE("Error: Unexpected Messenger window class"); } #endif if(g_wndMainMsg && !g_wndMainMsg->IsDestroyed()) delete g_wndMainMsg; g_wndMainMsg = new CMainMsgWnd(hwnd); } } else { TRACE("*** ERROR: main Messenger window can't be hooked"); } } } catch(...) { TRACE("ERROR: An exception was thrown in MessengerPlusGlobalHook (Main Messenger window)"); TRACEFLUSH; } } //Instant Message window else if(_tcscmp(szClass, CInstantMsgWnd::m_sClassName) == 0 || _tcscmp(szClass, CMobileMsgWnd::m_sClassName) == 0) { try { if(CPreferences::GetMPHookState() > 0) { if(!CHookedWnd::IsWindowHooked(hwnd)) { TRACE("Initialize will be called from Instant Message hook"); Initialize(); if(g_bInitialized) { if(_tcscmp(szClass, CMobileMsgWnd::m_sClassName) == 0) g_aMobileMsg->push_back(new CMobileMsgWnd(hwnd)); else g_aInstantMsg->push_back(new CInstantMsgWnd(hwnd)); } else { TRACE("*** ERROR: Instant Message window can't be hooked"); } } } else { if(g_mpWnd) g_mpWnd->StartGlobalTimer(); } } catch(...) { TRACE("ERROR: An exception was thrown in MessengerPlusGlobalHook (Instant Message window)"); TRACEFLUSH; } } //Notification window else if(_tcscmp(szClass, CNotificationWnd::m_sClassName4) == 0 || _tcscmp(szClass, CNotificationWnd::m_sClassName5) == 0) { try { if(CPreferences::GetMPHookState() > 0) { if(!CHookedWnd::IsWindowHooked(hwnd)) { TRACE("Initialize will be called from notification hook"); Initialize(); if(g_bInitialized) g_aNotificationWnd->push_back(new CNotificationWnd(hwnd)); else { TRACE("*** ERROR: notification window can't be hooked"); } } } else { if(g_mpWnd) g_mpWnd->StartGlobalTimer(); } } catch(...) { TRACE("ERROR: An exception was thrown in MessengerPlusGlobalHook (Notification window)"); TRACEFLUSH; } } //Systray hidden notification window else if(_tcscmp(szClass, CSysTrayWnd::m_sClassName4) == 0 || _tcscmp(szClass, CSysTrayWnd::m_sClassName5) == 0) { try { //Be sure that this is not one of the banned application that uses the same window class if(VerifyBannedApplication()) { if((!g_wndSysTrayMsg || !g_wndSysTrayMsg->IsWindowHooked()) && !CHookedWnd::IsWindowHooked(hwnd)) { TRACE("QuickInitialize will be called from systray window hook"); QuickInitialize(); if(g_bQuickInitialized) g_wndSysTrayMsg = new CSysTrayWnd(hwnd); else { TRACE("*** ERROR: systray window can't be hooked"); } } } } catch(...) { TRACE("ERROR: An exception was thrown in MessengerPlusGlobalHook (Systray window)"); TRACEFLUSH; } } } catch(...) { TRACE("ERROR: An exception was thrown in MessengerPlusGlobalHook"); TRACEFLUSH; } } //Properly chain the hooks return CallNextHookEx(g_hhGlobalHook, nCode, wParam, lParam); }