|
|
/*++
Copyright (C) Microsoft Corporation, 1997 - 1999
Module Name:
msgloop.cxx
Abstract:
This file contains the message pump for SENS.
Author:
Gopal Parupudi <GopalP>
[Notes:]
optional-notes
Revision History:
GopalP 11/5/1997 Start.
--*/
#include <precomp.hxx>
#include <dbt.h>
#define SENS_WINDOW_CLASS_NAME SENS_STRING("SENS Hidden Window class")
#define SENS_HIDDEN_WINDOW_NAME SENS_STRING("SENS")
#if defined(SENS_NT4)
#define SENS_MODULE_NAME SENS_STRING("SENS.EXE")
#else // SENS_NT4
#define SENS_MODULE_NAME SENS_STRING("SENS.DLL")
#endif // SENS_NT4
//
// Globals
//
HWND ghwndSens; DWORD gMessageLoopTid; HANDLE ghCleanupEvent; SYSTEM_POWER_STATUS gSystemPowerState;
LRESULT CALLBACK SensMainWndProc( HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam ) /*++
Routine Description:
Arguments:
None.
Return Value:
None.
--*/ { LRESULT lResult = TRUE;
#ifdef DETAIL_DEBUG
SensPrintA(SENS_INFO, ("SensMainWndProc(): Received a msg (0x%x) - (0x%x)\n", msg, wParam)); #endif // DETAIL_DEBUG
switch (msg) {
//
// Power Management Notifications.
//
case WM_POWERBROADCAST: { DWORD dwPowerEvent = (DWORD) wParam; SYSTEM_POWER_STATUS CurSPstate; SENSEVENT_POWER Data; BOOL bRet;
SensPrintA(SENS_INFO, ("SensMainWndProc(): Received WM_POWERBROADCAST msg - (0x%x)\n", wParam));
bRet = GetSystemPowerStatus(&CurSPstate); ASSERT(bRet);
switch (dwPowerEvent) { case PBT_APMBATTERYLOW: { // Save the new state. A critsec is not necessary as this Message to be serialized.
memcpy(&gSystemPowerState, &CurSPstate, sizeof(SYSTEM_POWER_STATUS));
Data.eType = SENS_EVENT_POWER_BATTERY_LOW; memcpy(&Data.PowerStatus, &CurSPstate, sizeof(SYSTEM_POWER_STATUS));
// Fire BatteryLow event
SensFireEvent(&Data);
break; }
case PBT_APMPOWERSTATUSCHANGE: { //
// OnACPower event is fired when
// o previously the machine was not on AC
// o now, it is on AC
//
if ( (CurSPstate.ACLineStatus == AC_LINE_ONLINE) && (gSystemPowerState.ACLineStatus != AC_LINE_ONLINE)) { Data.eType = SENS_EVENT_POWER_ON_ACPOWER; } else //
// OnBatteryPower event is fired when
// o previously the machine was on AC
// o now, it is not on AC
// o the machine has a system battery
//
if ( (CurSPstate.ACLineStatus == AC_LINE_OFFLINE) && (gSystemPowerState.ACLineStatus == AC_LINE_ONLINE) && ((CurSPstate.BatteryFlag & BATTERY_FLAG_NO_BATTERY) == 0)) { Data.eType = SENS_EVENT_POWER_ON_BATTERYPOWER; } //
// A Power change we don't care about.
//
else { break; }
// Save the new state. A critsec is not necessary as this Message to be serialized.
memcpy(&gSystemPowerState, &CurSPstate, sizeof(SYSTEM_POWER_STATUS));
memcpy(&Data.PowerStatus, &CurSPstate, sizeof(SYSTEM_POWER_STATUS));
// Fire the event.
SensFireEvent(&Data);
break; }
default: // Unrecognized Power event.
break;
} // switch (dwPowerEvent)
break; }
#if defined(SENS_CHICAGO)
//
// PnP Device Notifications.
//
case WM_DEVICECHANGE: { SensPrintA(SENS_INFO, ("SensMainWndProc(): Received a WM_DEVICECHANGE msg - (0x%x)\n", wParam));
PDEV_BROADCAST_NET pdbNet = (PDEV_BROADCAST_NET) lParam;
switch (wParam) { case DBT_DEVICEARRIVAL: { if (pdbNet->dbcn_devicetype == DBT_DEVTYP_NET) { SENSEVENT_PNP Data;
ASSERT(pdbNet->dbcn_size == sizeof(DEV_BROADCAST_NET));
Data.eType = SENS_EVENT_PNP_DEVICE_ARRIVED; Data.Size = pdbNet->dbcn_size; Data.DevType = pdbNet->dbcn_devicetype; Data.Resource = pdbNet->dbcn_resource; Data.Flags = pdbNet->dbcn_flags;
SensFireEvent(&Data);
// Force a recalculation of LAN Connectivity
gdwLastLANTime -= (MAX_LAN_INTERVAL + 1);
//EvaluateConnectivity(TYPE_LAN);
} break; }
case DBT_DEVICEREMOVECOMPLETE: { if (pdbNet->dbcn_devicetype == DBT_DEVTYP_NET) { SENSEVENT_PNP Data;
ASSERT(pdbNet->dbcn_size == sizeof(DEV_BROADCAST_NET));
Data.eType = SENS_EVENT_PNP_DEVICE_REMOVED; Data.Size = pdbNet->dbcn_size; Data.DevType = pdbNet->dbcn_devicetype; Data.Resource = pdbNet->dbcn_resource; Data.Flags = pdbNet->dbcn_flags;
SensFireEvent(&Data);
// Force a recalculation of LAN Connectivity
gdwLastLANTime -= (MAX_LAN_INTERVAL + 1);
//EvaluateConnectivity(TYPE_LAN);
} break; } }
break; }
#endif // SENS_CHICAGO
case WM_SENS_CLEANUP: //
// Cleanup the Window resources of SENS
//
PostQuitMessage(0);
break;
default: lResult = DefWindowProc(hwnd, msg, wParam, lParam); break;
} // switch (msg)
return lResult; }
DWORD WINAPI SensMessageLoopThreadRoutine( LPVOID lpParam ) /*++
Routine Description:
Arguments:
None.
Return Value:
None.
--*/ { WNDCLASS wc; BOOL f; BOOL bRet; HINSTANCE hInstance = NULL; MSG msg;
//
// Save away the ThreadId
//
gMessageLoopTid = GetCurrentThreadId();
//
// Save a snapshot of the System Power State.
//
bRet = GetSystemPowerStatus(&gSystemPowerState); if (bRet == FALSE) { SensPrintA(SENS_ERR, ("SensMessageLoopThread(): GetSystemPowerStatus() failed with " "GLE = %d\n", GetLastError())); }
//
// Create an event to signal the cleanup of all window resources.
//
ghCleanupEvent = CreateEvent( NULL, // Handle cannot be inherited
FALSE, // It is an auto-reset event
FALSE, // Intial state is non-signalled
SENS_STRING("Sens Hidden Window Cleanup Event") // Name of the event
); if (ghCleanupEvent == NULL) { SensPrintA(SENS_ERR, ("ServiceStart(): CreateEvent(ghCleanupEvent)" " failed with %d.", GetLastError())); }
//
// Register window class
//
hInstance = GetModuleHandle(SENS_MODULE_NAME); ASSERT(hInstance);
memset(&wc, 0x0, sizeof(WNDCLASS));
wc.style = 0; wc.lpfnWndProc = (WNDPROC) SensMainWndProc; wc.cbClsExtra = 0; wc.cbWndExtra = 0; wc.hIcon = NULL; wc.hInstance = hInstance; wc.hCursor = NULL; wc.hbrBackground = NULL; wc.lpszMenuName = NULL; wc.lpszClassName = SENS_WINDOW_CLASS_NAME;
f = RegisterClass(&wc); ASSERT(f);
// Create a hidden window
ghwndSens = CreateWindow( SENS_WINDOW_CLASS_NAME, // Class Name
SENS_HIDDEN_WINDOW_NAME, // Window Name
NULL, // Window Style
0, // Horizontal position
0, // Vertical position
0, // Window width
0, // Window height
NULL, // Handle to parent window
NULL, // Handle to menu
hInstance, // Handle to application instance
NULL // window creation data
); if (ghwndSens) { ShowWindow(ghwndSens, SW_HIDE);
//
// Message pump.
//
while ((bRet = GetMessage(&msg, ghwndSens, NULL, NULL)) > 0) { TranslateMessage(&msg); DispatchMessage(&msg); }
#ifdef DETAIL_DEBUG
SensPrintA(SENS_DBG, ("SensMessageLoopThread(): Out of message pump !\n")); #endif // DETAIL_DEBUG
// Check for bad return value from GetMessage()
if (bRet == -1) { SensPrintA(SENS_ERR, ("SensMessageLoopThread(): GetMessage() failed with GLE of %d\n", GetLastError())); }
BOOL bRet;
// Cleanup the window.
bRet = DestroyWindow(ghwndSens); ASSERT(bRet); if (bRet != TRUE) { SensPrintA(SENS_ERR, ("SensMessageLoopThread(): DestroyWindow() failed with %d\n", GetLastError())); }
// Unregister the window class
bRet = UnregisterClass(SENS_WINDOW_CLASS_NAME, hInstance); ASSERT(bRet);
// Window cleanup done. Set the event.
if (ghCleanupEvent) { SetEvent(ghCleanupEvent); } } else { SensPrintA(SENS_ERR, ("SensMessageLoopThread(): CreateWindow() failed with GLE of %d\n", GetLastError())); }
return 0; }
BOOL InitMessageLoop( void ) /*++
Routine Description:
Arguments:
None.
Return Value:
None.
--*/ { #if defined(SENS_CHICAGO)
BOOL bStatus; HANDLE hThread; DWORD dwThreadId;
bStatus = FALSE;
hThread = CreateThread( NULL, 0, SensMessageLoopThreadRoutine, NULL, 0, &dwThreadId ); if (NULL != hThread) { bStatus = TRUE; CloseHandle(hThread); } else { SensPrintA(SENS_INFO, ("InitMessageLoop() returning %d with GLE of %d\n", bStatus, GetLastError())); }
return bStatus;
#else // SENS_CHICAGO
return TRUE;
#endif // SENS_CHICAGO
}
|