netripper

netripper

Dec 27th, 2009
69
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 6.00 KB | None | 0 0
  1. // KeypadLedControl.cpp : Defines the entry point for the console application.
  2. //
  3.  
  4. #include "stdafx.h"
  5. #include <windows.h>
  6. #include <pmpolicy.h>
  7.  
  8. // From MSDN: http://msdn.microsoft.com/en-us/library/ms838354.aspx
  9. #pragma region Power management defines
  10.  
  11. // GDI Escapes for ExtEscape()
  12. #define QUERYESCSUPPORT    8
  13.  
  14. // The following are unique to CE
  15. #define GETVFRAMEPHYSICAL   6144
  16. #define GETVFRAMELEN    6145
  17. #define DBGDRIVERSTAT    6146
  18. #define SETPOWERMANAGEMENT   6147
  19. #define GETPOWERMANAGEMENT   6148
  20.  
  21. typedef struct _VIDEO_POWER_MANAGEMENT {
  22.     ULONG Length;
  23.     ULONG DPMSVersion;
  24.     ULONG PowerState;
  25. } VIDEO_POWER_MANAGEMENT, *PVIDEO_POWER_MANAGEMENT;
  26.  
  27. typedef enum _VIDEO_POWER_STATE {
  28.     VideoPowerOn = 1,
  29.     VideoPowerStandBy,
  30.     VideoPowerSuspend,
  31.     VideoPowerOff
  32. } VIDEO_POWER_STATE, *PVIDEO_POWER_STATE;
  33.  
  34. #pragma endregion // Power management defines
  35.  
  36. int _tmain(int argc, _TCHAR* argv[])
  37. {
  38.     // Create an event for ourselves, so that we can be turned off as well
  39.     HANDLE appEvent = CreateEvent(NULL, TRUE, FALSE, L"KeypadLedControlApp");
  40.     if (appEvent == NULL)
  41.     {
  42.         MessageBox(NULL, L"Couldn't create an event for ourselves", L"Error", MB_OK);
  43.         return 1;
  44.     }
  45.  
  46.     // If the app is already running, we set the event so that it will close itself.
  47.     if (GetLastError() == ERROR_ALREADY_EXISTS)
  48.     {
  49.         SetEvent(appEvent);
  50.         CloseHandle(appEvent);
  51.         return 1;
  52.     }
  53.  
  54.     // Get the keyped led event (this one is used for Leo at least)
  55.     HANDLE iconOnEvent = CreateEvent(NULL, TRUE, FALSE, L"IconLedOnEvent");
  56.     if (iconOnEvent == NULL)
  57.     {
  58.         // Oops, error creating the event?
  59.         MessageBox(NULL, L"Couldn't create the 'IconLedOnEvent' keypad light event", L"Error", MB_OK);
  60.         return 1;
  61.     }
  62.     if (GetLastError() != ERROR_ALREADY_EXISTS)
  63.     {
  64.         // This even didn't exist yet. Let's see if we can try another event (it's IconLedEvent for Rhodium)
  65.         CloseHandle(iconOnEvent);
  66.         iconOnEvent = CreateEvent(NULL, TRUE, FALSE, L"IconLedEvent");
  67.         if (iconOnEvent == NULL)
  68.         {
  69.             MessageBox(NULL, L"Couldn't create the 'IconLedEvent' keypad light event", L"Error", MB_OK);
  70.             return 1;
  71.         }
  72.         if (GetLastError() != ERROR_ALREADY_EXISTS)
  73.         {
  74.             // This event didn't exist either.
  75.             MessageBox(NULL, L"Sorry, this device is not supported it seems", L"Error", MB_OK);
  76.             CloseHandle(iconOnEvent);
  77.             return 1;
  78.         }
  79.     }
  80.  
  81.     // Get the keypad led event to turn it off
  82.     HANDLE iconOffEvent = CreateEvent(NULL, TRUE, FALSE, L"IconLedOffEvent");
  83.     if (iconOffEvent == NULL)
  84.     {
  85.         // Oops, error creating the event?
  86.         MessageBox(NULL, L"Couldn't create the 'IconLedOffEvent' keypad light event", L"Error", MB_OK);
  87.         return 1;
  88.     }
  89.     if (GetLastError() != ERROR_ALREADY_EXISTS)
  90.     {
  91.         // This event didn't exist yet. This means this device does not use this event. Which means we will just ignore it and hope
  92.         // the keypad lights goes off automatically when it goes into standby.
  93.         CloseHandle(iconOffEvent);
  94.         iconOffEvent = NULL;
  95.     }
  96.  
  97.     // Check if the driver supports power management information
  98.     HDC gdc = GetDC(NULL);
  99.     int iESC = GETPOWERMANAGEMENT;
  100.     if (ExtEscape(gdc, QUERYESCSUPPORT, sizeof(int), (LPCSTR)&iESC, 0, NULL) == 0)
  101.     {
  102.         MessageBox(NULL, L"This device does not support checking for LCD state", L"Error", MB_OK);
  103.         CloseHandle(iconOnEvent);
  104.         ReleaseDC(NULL, gdc);
  105.         return 1;
  106.     }
  107.  
  108.     // Request that we stay in UNATTENDED power mode, so that we keep getting CPU cycles while LCD is turned off
  109.     // We must keep track of unattended mode. It uses a refcount. If we would forget to release, the device would never enter real standby anymore = battery drain.
  110.     bool bUsingUnattendedMode = true;
  111.     bool res = PowerPolicyNotify(PPN_UNATTENDEDMODE, TRUE);
  112.  
  113.     // Variables for the loop. To prevent overhead we create these variables outside the loop.
  114.     VIDEO_POWER_MANAGEMENT pm;
  115.     pm.Length = sizeof(pm);
  116.     int ret;
  117.     while (true)
  118.     {
  119.         // Get current power management information
  120.         ret = ExtEscape(gdc, GETPOWERMANAGEMENT, 0, NULL, pm.Length, (LPSTR)&pm);
  121.  
  122.         // Check the power state
  123.         if (pm.PowerState == VideoPowerOn)
  124.         {
  125.             // LCD is on, set the event so that the keypad lights go on
  126.             SetEvent(iconOnEvent);
  127.  
  128.             // Also enable unattended mode if it wasn't already enabled
  129.             if (!bUsingUnattendedMode)
  130.             {
  131.                 PowerPolicyNotify(PPN_UNATTENDEDMODE, TRUE);
  132.                 bUsingUnattendedMode = true;
  133.             }
  134.         }
  135.         else
  136.         {
  137.             // LCD is either in standby, suspend or off. Set the event to turn keypad lights off (if we can).
  138.             if (iconOffEvent != NULL)
  139.             {
  140.                 SetEvent(iconOffEvent);
  141.             }
  142.  
  143.             // And release unattended mode
  144.             if (bUsingUnattendedMode)
  145.             {
  146.                 PowerPolicyNotify(PPN_UNATTENDEDMODE, FALSE);
  147.                 bUsingUnattendedMode = false;
  148.             }
  149.         }
  150.        
  151.         // We'll keep on running this app as long as the event hasn't been set (by starting this app again)
  152.         // Use a 1-second delay. This means that:
  153.         // - If the device goes into standby, it may take up to 1 second before the keypad light goes off (i.e. for Rhodium where
  154.         //   keypad is not turned off by the driver).
  155.         // - The device won't stay in unattended mode longer than 1 second, as the LCD power is re-evaluated within this time and
  156.         //   unattended mode is released when LCD is off after setting the event. This prevents power drain.
  157.         if (WaitForSingleObject(appEvent, 1000) != WAIT_TIMEOUT)
  158.         {
  159.             break;
  160.         }
  161.     }
  162.  
  163.     // Cleanup
  164.     ReleaseDC(NULL, gdc);
  165.     CloseHandle(iconOnEvent);
  166.     CloseHandle(appEvent);
  167.     if (iconOffEvent != NULL)
  168.     {
  169.         CloseHandle(iconOffEvent);
  170.     }
  171.     if (bUsingUnattendedMode)
  172.     {
  173.         PowerPolicyNotify(PPN_UNATTENDEDMODE, FALSE);
  174.         bUsingUnattendedMode = false;
  175.     }
  176.    
  177.     return 0;
  178. }
  179.  
  180.  
Add Comment
Please, Sign In to add comment