Windows Vista如何以SYSTEM權限啟動進程(1)(圖)
SYSTEM帳戶啟動的實質
其實不管用哪種方法,其本質都一樣。都是利用SYSTEM登錄會話里已有的某個進程A,幫助我們創建一個進程B,進程B會自然而然地運行在SYSTEM登錄會話里-從而具有SYSTEM權限。
這里提到登錄會話(Logon Session)的概念,這個概念比較抽象,甚至連MSDN里都有點語焉不詳。這里我們且不去管它(將會在后續的文章里給大家細述這個抽象概念)。只需要了解:登錄會話用來代表特定的安全主體,代表該安全主體的一次登錄實例。
每個進程,都必須運行在特定的登錄會話里。這里就有一個問題,在用戶登錄之前,Windows系統里已經運行了一些進程,這些進程顯然也應該運行在登錄會話里,這就是所謂的SYSTEM登錄會話,它所代表的安全主體就是SYSTEM帳戶。
在Windows的安全機制里,特定登錄會話里的某個進程所啟動的其他進程,也會運行在該登錄會話里,從而繼承安全上下文。
《以System帳戶身份運行應用程序的三種辦法》這篇文章所描述的方法,都是運用這種原理。例如借助At命令以SYSTEM帳戶身份啟動進程,實際上是由Task Scheduler服務啟動的,而Task Scheduler服務所在的進程svchost正是運行在SYSTEM登錄會話,如附圖所示。
圖中所示的Task Scheduler服務的進程svchost所在的登錄會話ID(Logon Session ID)是0x0-3e7,這就是代表SYSTEM登錄會話。
用Psexec命令,道理也一樣,實際上啟動進程的是PsexecSvc服務,該服務的進程運行在SYSTEM登錄會話。
如何讓用戶能夠看到SYSTEM下的進程? 在Windows 2000/XP下,這個不是什么問題。然而在Windows Vista下問題就來了。如果企圖用AT命令啟動某個Local SYSTEM進程,就會警告說不能和用戶進行交互,哪怕加上/Interactive參數也不行! 原來在Windows Vista下,存在一個會話0隔離的問題。而AT命令所對應的Task Scheduler服務運行在會話0,而會話0是不能和用戶進行交互的。 盆盆評注:這里要注意,會話和登錄會話,是兩碼事。具體的介紹,敬請期待后續的文章。 原來在會話0里,并沒有WinSta0這個窗口站。天哪,又來了一個窗口站的概念,嗯,先不用管它,這里只需理解,窗口站用來保護進程的用戶界面。只有WinSta0這個特殊的窗口站才可以接受用戶的鼠標、鍵盤事件,才能和用戶進行交互。 在Windows系統里,如果沒有特別指定,SYSTEM登錄會話里的進程,將會默認運行在Service-0X0-3E7$窗口站里,所以無法和用戶進行交互。 所以很顯然,要讓以SYSTEM權限運行的進程,能夠和用戶進行交互,必須滿足以下條件: 1. 必須不能運行在會話0下,例如可以運行在當前用戶所在的會話下(例如會話1、2等) 2. 該SYSTEM進程必須運行在WinSta0窗口站。 對于開發人員來說,推薦參考Leo Jiang朋友的Blog文章,以便了解如何通過編程的方法,創建運行在WinSta0里的Local SYSTEM進程。 而對于IT Pro來說,我們可以借助Mark Russinovich所寫的Psexec工具,讓任意指定的進程運行在SYSTEM權限下。 而對于Windows Vista來說,其實有好些Local SYSTEM進程本身運行在WinSta0下(非會話0),例如Winlogon進程、某個csrss進程,還有我們大家很熟悉的UAC提示對話框(consent進程),都運行在SYSTEM下,但是可以和用戶進行交互。 google_protectAndRun('render_ads.js::google_render_ad', google_handleError, google_render_ad);