發行日期:2025年2月25日
版本:.NET 8 及更新版本 .NET Framework 所有版本
摘要
Microsoft推出最新版 Windows 的安全性改良功能。 這些安全性改進會修改範本路徑處理,並可能導致某些 .NET Framework 和 .NET API,例如System.IO.Path.GetTempPath()在套用修補程式之後傳回不同的位置。
需要採取動作
任何 .NET Framework 或都不需要採取任何動作。NET 型應用程式。 您的應用程式會自動受益於任何適用於您環境的安全性改良功能。 大部分應用程式不會觀察任何行為變更。
本文其餘部分詳述如何判斷這些安全性改良功能是否會影響應用程式的運行時間行為。 如有需要,本文也會列出自定義運行時間行為的步驟
適用軟體
本文適用於下列軟體:
-
.NET 8 及更新版本
-
.NET Framework 2024 年 7 月為止的所有版本安全性更新和後續更新
只有在執行下列 Windows 更新版本時:
-
Windows 10 安裝 KB5052077 時的版本 22H2
-
Windows Server 2019 年安裝 KB5053594
-
Windows Server 2016 安裝KB5053594時
本文不適用於在 Windows 11、Windows Server 2022 或更新版本上執行的 .NET Framework 或 .NET。
本文 不 適用於在非 Windows 平台上執行的 .NET。
詳細描述和影響陳述
自上述 Windows 更新 KB 起,Microsoft已將 Win32 GetTempPath2 API 退回舊版的 Windows,以做為較舊的 Win32 GetTempPath API 更安全的替換品。 內部,.NET Framework 和 .NET 仰賴這些 Win32 API 來提供 System.IO.Path.GetTempPath() 方法的實作:如果 Win32 GetTempPath2 API 存在,則會偏好使用;如果 GetTempPath2 不存在,Win32 GetTempPath API 則會用作後援。
由於這些 KB 讓新的 Win32 GetTempPath2 API 可在適用的平臺上使用,因此在安裝 KB 之後,.NET Framework 和 .NET 將會開始使用 GetTempPath2。
主要的行為變更是,以 SYSTEM 身分識別執行的來電者預設會觀察 System.IO.Path.GetTempPath() 方法傳回 %WINDIR%\SystemTemp ,而執行系統身分識別以外的任何專案之來電者則會觀察該方法繼續傳回其現有值。
如果您的應用程式符合下列 所有 準則,您可能會受到此變更的影響:
-
您的應用程式會使用列在舊版「適用軟體」標題下的運行時間和作系統平臺;和
-
您的應用程式會以 SYSTEM 身分識別執行;和
-
您手動設定 %TMP% 或 %TEMP% 環境變數,以重新導向標準範本檔案位置。 (參閱 Win32 GetTempPath API 檔的一 節 。)
如果您符合 所有這些 準則,則安裝 Windows KB 之後,您可能會觀察應用程式在您預定目錄以外的範本目錄中書寫。
此行為變更可能透過任何 .NET Framework 或顯示。NET 提供的 API 最終仰賴 GetTempPath2。 最常見的進入點如下:
這並不是完整的方法清單,一旦安裝 KB 后,其行為可能會變更。
判斷應用程式是否在系統身分識別下執行
有幾個不同的機制可以判斷 .NET Framework 或 .NET 應用程式的身分識別
IIS 型 Web 應用程式
IIS 將 SYSTEM 身分識別稱為「本地人YSTEM」。 在 [IIS 管理員] (inetmgr.exe) 中,移至 [應用程式集區] 索引標籤,查看所有應用程式集區及其相關身分識別。 您也可以從 [ 群組 ] 下拉式清單中選取 [身分識別],以便更輕鬆地查看以[本地人身分識別] 執行的應用程式集區。
下方螢幕快照顯示應用程式集區 (“MyAppPool”) 的範例,此 ) 設定為[本地人YSTEM]。 在此應用程式集區中執行的任何應用程式都會以系統身分識別執行。
您也可以使用下列腳本,以程序設計方式從提升許可權的PowerShell作業階段存取這項資訊。
Import-Module IISAdministration Get-IISAppPool | where {$_.ProcessModel.IdentityType -eq "LocalSystem"}
在已設定系統層級 「MyAppPool」應用程式集區的計算機中,如上圖所示,此 PowerShell 腳本會列印下列內容,顯示「MyAppPool」正在系統身分識別底下執行。
Name Status CLR Ver Pipeline Mode Start Mode ---- ------ ------- ------------- ---------- MyAppPool Started v4.0 Integrated OnDemand
Windows 服務
如果您 .NET Framework 或 。NET 型應用程式已註冊為 Windows 服務,您可以使用服務管理員來檢視其相關聯的身分識別。
從提升許可權的命令提示字元執行 services.msc。 這會顯示服務管理員 UI。
如果 [ 登入 為] 欄列出服務身分識別的 [本機系統],則服務是在 [系統身分識別] 下執行。
您也可以使用 Get-Service cmdlet 透過 PowerShell 查詢此資料。 例如,若要查詢名為 MyService之服務的這項資訊,請使用下列命令。
(Get-Service MyService).UserName -ieq "LocalSystem"
如果服務已註冊為在 SYSTEM 身分識別下執行,這會將 True 印到主機。
其他機制
任務管理員 (taskmgr.exe) 或 Sysinternals 程式總管 等工具也可以告訴您,系統身分識別下是否有執行的應用程式。
在 [任務管理器] 中,使用 [詳細數據] 檢視列出系統中的所有執行程式,然後找出感興趣的程式,然後查看 [ 用戶名稱 ] 欄底下的專案。
如果 [用戶名稱] 值為 “SYSTEM”,則程式會在 [系統身分識別] 下執行。
或者,在 [Sysinternals 程式總管] 中,找出感興趣的程式,然後輸入 [ 內容 ] 檢視,然後查看 [ 圖像 ] 索引卷標底下的 [使用者] 字段。
如果 使用者 值為 「NT AUTHORITY\SYSTEM」,則此程式會在 SYSTEM 身分識別下執行。
變更系統層級程式的範本路徑
下列 PowerShell 腳本示範如何建立新的目錄 C:\NewSystemTemp\ ,以及將目錄存取權限在 SYSTEM 身分識別下執行的程式。 請勿嘗試變更已填入檔案之目錄的 ACL。
此腳本必須從提升許可權的 PowerShell 工作階段執行。
mkdir C:\NewSystemTemp\ $acl = New-Object System.Security.AccessControl.DirectorySecurity $acl.SetSecurityDescriptorSddlForm("O:SYG:SYD:PAI(A;OICI;FA;;;SY)(A;OICI;FA;;;BA)") Set-Acl C:\NewSystemTemp\ -AclObject $acl
您可以執行命令來確認此作業成功
icacls C:\NewSystemTemp\
這會產生下列輸出結果,顯示成功:
C:\NewSystemTemp\ NT AUTHORITY\SYSTEM:(OI)(CI)(F) BUILTIN\Administrators:(OI)(CI)(F) Successfully processed 1 files; Failed processing 0 files
建立目錄后,使用系統層級範圍設定 %SYSTEMTEMP% 環境變數。 您可以透過系統 控制台 UI 進行設定,也可以透過 PowerShell 以程式設計方式進行設定:
[Environment]::SetEnvironmentVariable("SYSTEMTEMP", "C:\NewSystemTemp", [EnvironmentVariableTarget]::Machine)
然後將電腦重新啟動。
變更 %SYSTEMTEMP% 環境變數並不會變更以 SYSTEM 以外的身分識別執行的 .NET Framework 和 .NET 應用程式 System.IO.Path.GetTempPath() 傳回值。 這些應用程式會繼續遵循與往常相同的解析度邏輯,包括尊重 %TMP% 或 %TEMP% 環境變數。
同樣地,設定 %TMP% 或 %TEMP% 環境變數並不會變更以 SYSTEM 身分識別執行的 .NET Framework 和 .NET 應用程式之 System.IO.Path.GetTempPath() 傳回值。
如需詳細資訊
如需 .NET Framework 和 .NET 行為的詳細資訊,請參閱 Path.GetTempPath 上的 .NET 檔。
如需有關基礎 Windows OS 行為的詳細資訊,請參閱 Win32 GetTempPath2 API 上的 Windows 檔。