Wince6.0 電源控制驅動程序分析-基於S5PC100

     在wince6.0裏有一個電源控制模塊驅動(Power Controller Driver),該模塊主要是反映和控制系統電源狀態,以及控制系統硬件模塊的電源狀態。該驅動也是典型的流式驅動,提供以下接口:

其中主要的是PWC_Init和PWC_IOControl,其餘的那些函數都是空函數,僅僅提供接口而已。那接下來我們就來分析PWC_Init和PWC_IOControl.

1.PWC_Init

該函數主要是做一些初始化操作,包括初始化電源控制寄存器和硬件模塊控制寄存器(包括攝像頭、JPEG解碼器、TVOUT、IP電話等)。

寄存器的初始化主要是通過MmMapIoSpace將寄存器的地址映射到虛擬地址空間。接着創建系統電源監視線程:

    g_hThreadPowerMon = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE) PowerMonitorThread, NULL, 0, NULL);
    if (g_hThreadPowerMon == NULL )
    {
        RETAILMSG(PWC_ZONE_ERROR,(_T("[PWRCON:ERR] %s->CreateThread() Power Monitor Failed /n"), _T(__FUNCTION__)));
        goto CleanUp;
    }

也就是說系統電源狀態的監視和設置是在該線程中完成的,PowerMonitorThread函數具體代碼如下:

該函數看起來雖然複雜,但結構和流程上去不復雜。首先要明白一點,系統電源的變化是通過消息事件機制通信的,因此必須要創建一個消息隊列: g_hMsgQueue = CreateMsgQueue(NULL, &msgOptions);其中的參數msgOptions是一個消息隊列結構體,它定義了該隊列的屬性:

typedef MSGQUEUEOPTIONS_OS{
  DWORD dwSize;
  DWORD dwFlags;
  DWORD dwMaxMessages;
  DWORD cbMaxMessage;
  BOOL bReadAccess;
} MSGQUEUEOPTIONS, FAR* LPMSGQUEUEOPTIONS, *PMSGQUEUEOPTIONS;

    消息通信機制在wince中是很重要的一點,通過它可以實現驅動程序之間,驅動程序與應用程序之間的通信。

   接着又是一個很重要的函數:

  // Request Power notifications
    hPowerNotification = RequestPowerNotifications(g_hMsgQueue, POWER_NOTIFY_ALL);
    if (!hPowerNotification)
    {
        RETAILMSG(PWC_ZONE_ERROR,(_T("[PWRCON:ERR] %s->RequestPowerNotifications() Failed : Err %d/n"), _T(__FUNCTION__), GetLastError()));
        goto Thread_CleanUp;
    }
函數equestPowerNotifications使電源管理器在發現系統電源狀態變化時向它發出通知,即電源狀態變化了!它的第一個參數就是上面創建消息隊列時得到的句柄,第二個參數POWER_NOTIFY_ALL意思是獲取電源任何變化的通知。

       到這裏基本工作已經完成,即創建了消息隊列,也告訴了電源管理器當系統電源狀態改變時發出通知。那麼接下來要做的就是接受這些通知並進行相應的操作。這部分主要代碼如下:

 

    這裏是通過輪詢的方式去查看是否有電源狀態改變的消息,該函數是:ReadMsgQueue(g_hMsgQueue, msgBuf, QUEUE_SIZE, &iBytesInQueue, INFINITE, &dwFlags);如果讀到了消息就返回相應的值,否則返回NULL.

     得到相應的消息後就要進行處理了,這裏採用的是結構清晰的switch-case語句,即不同的消息進行不同的處理或打印出提示信息這部分比較簡單,這裏就不在多少。有一點要提醒,當推出線程的時候記得停止接受電源管理器的消息和關閉消息隊列的句柄:

 StopPowerNotifications(hPowerNotification);

CloseMsgQueue(g_hMsgQueue);

      當該驅動程序被加載以後上述監視線程就開始工作了,直到被關閉。從其代碼可以看出,該監視線程只能監視系統電源狀態的變化並不能進行控制。那麼如何去控制系統的電源狀態和系統硬件模塊的電源狀態呢?很顯然要用到PWC_IOControl了。

2。PWC_IOControl

     PWC_IOControl就是驅動程序提供給上層應用程序的接口用來控制系統和硬件模塊的的電源狀態。怎麼控制呢?發命令!詳細大家對XXX_IOControl的結構十分清晰,我也列出器代碼:

     代碼雖然長,但並不複雜,邏輯上還是很簡單的。從其代碼可以看出它的控制操作主要分爲兩種:IOCTL_PWRCON_SET_POWER_ON,IOCTL_PWRCON_SET_POWER_OFF,即關閉電源和打開電源。這兩種操作是針對所以硬件模塊來做的,沒有具體到控制其中的一個硬件模塊,如攝像頭。當然我們可以添加自己的命令進行更爲靈活的電源控制。

      整體來看該驅動比較簡單,難點就是怎麼把它用活,用巧。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章