ユーザーインターフェイス特権の分離
出典: フリー百科事典『ウィキペディア(Wikipedia)』 (2025/02/09 05:01 UTC 版)
ユーザーインターフェイス特権の分離 (英語: User Interface Privilege Isolation, UIPI)[1] とは、Windows Server 2008/Vista以降に、シャッターアタック(Shatter Attack、壊滅的攻撃)を防ぐために導入されたセキュリティ機能である。Windows NT 4.0以降、Object Managerを介して生成されるオブジェクトにはセキュリティ記述子が与えられ、そうしたオブジェクトへのアクセス制御は可能であったが、ウィンドウオブジェクトにはセキュリティ記述子は与えられず、ウィンドウ自体へのセキュリティ制御はできなかった。
UIPIと必須整合性制御により、同じ対話型デスクトップ内で管理者よりも低いアカウントとして実行されているプロセス(lower IL)から、完全な管理者として実行されているプロセス(high IL)を分離できる。したがって、権限の低いプロセスは、DLLインジェクションやウィンドウメッセージAPI(SendMessage/PostMessage等)など、任意のコードを他プロセスに実行させることのできる操作をより高い権限を持つプロセスに対して実行できない。
機能
Windowsでは、任意のウィンドウオブジェクトを取得してそのオブジェクトに対してデータを送信する(WM_SETTEXT
)ことができるが、言い換えれば、悪意のあるデータを送りつけることが可能である。次の例において、もしメモ帳のプロセスが高い整合性レベルで実行されている場合、UIPIはこうした書き込みをブロックする[2]。
// ウインドウクラスを元に、メモ帳のウインドウを検索
HWND hwndNotepad = FindWindow(L"notepad", NULL);
// メモ帳のウインドウからエディトコントロールを取得
HWND hWndEdit;
EnumChildWindows(hWndEdit, EnumChildProc, (LPARAM)&hWndEdit);
// エディトコントロールに任意のテキストを設定
BOOL bResult = SendMessage(hWndEdit, WM_SETTEXT, 0, (LPARAM)L"text");
ただし、WM_NULL
、WM_MOVE
、WM_SIZE
、WM_GETTEXT
、WM_GETTEXTLENGTH
、WM_GETHOTKEY
、WM_GETICON
、WM_RENDERFORMAT
、WM_DRAWCLIPBOARD
、WM_CHANGECBCHAIN
、WM_THEMECHANGED
はUIPIのブロックする対象ではない。特に、WM_GETTEXT
がブロックされないということは、高ILで実行されているプロセスのウィンドウオブジェクトのデータを読み取ることはできるということである[2]。
WCHAR wszBuffer[1024];
bResult = SendMessage(hWndEdit, WM_GETTEXT, sizeof(wszBuffer) / sizeof(WCHAR), (LPARAM)wszBuffer);
シャッター攻撃において、バッファーフローを引き起こせるメッセージはWM_COPYDATA
とWM_DROPFILES
などがある。例えば、送信側はWM_COPYDATA
の自身のサイズ(cbData
)を自由に設定できるため、もし受信側が受け取るサイズを静的に定義しているとオーバーフローが起こる可能性がある。当然、UIPIはこれを防ぐため導入されたため、このようなメッセージを低ILプロセスから高ILプロセスに送ることはできない[2]。
WCHAR wszData[] = L"message";
COPYDATASTRUCT data = { 0 };
data.cbData = sizeof(wszData); // 0xFFFFFFFFでもよい。
data.lpData = wszData;
SendMessage(hWndTarget, WM_COPYDATA, (WPARAM)hWnd, (LPARAM)&data);
無効化
特定の種類のメッセージのフィルターを無効化
整合性レベル「中(Medium)」以上のプロセスは、ChangeWindowMessageFilterEx
を使用して、特定の種類のメッセージを許可することができる[2]。
マニフェストによる完全無効化
例えば、osk.exe
は画面にキーボードUIを表示し、 ユーザーがキーをクリックすると、その入力を背後のウインドウに送信する。 もし、背後のウインドウが昇格したプロセスによって作成されていても、UIPIによってブロックされるべきではない。
こうしたUIアクセシビリティソフトウェアのような、他のソフトウェアのUIにアクセスするソフトウェアはUIPIが障壁となる。そのため、Windowsは以下の条件を満たしている場合に限り、UIPIの無効化を提供する。
- デジタル署名されている。
%SystemRoot%
もしくは%ProgramFiles%
にインストールされている。- アプリケーションマニフェストで
uiAccess
値がtrue
である。 <?xml version="1.0" encoding="utf-8"?> <asmv1:assembly manifestVersion="1.0" xmlns="urn:schemas-microsoft-com:asm.v1" xmlns:asmv1="urn:schemas-microsoft-com:asm.v1" xmlns:asmv2="urn:schemas-microsoft-com:asm.v2" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"> <assemblyIdentity version="1.0.0.0" name="MyApplication.app"/> <trustInfo xmlns="urn:schemas-microsoft-com:asm.v2"> <security> <requestedPrivileges xmlns="urn:schemas-microsoft-com:asm.v3"> <requestedExecutionLevel level="..." uiAccess="true" /> </requestedPrivileges> </security> </trustInfo> </asmv1:assembly>
Windows全体で完全に無効化
脚注
- ユーザーインターフェイス特権の分離のページへのリンク