アドレス空間
プロセスには限られたアドレス空間があります。32ビットで動作している場合、プロセスにはおよそ 2 GB (<0x7fffffff) のプロセスアドレス空間と、 2 GB (>0x8000000) のカーネルモード用のものがあり、それらを使って遊ぶことができます。メモリ割り当て、ファイルマッピング、 DLLs、その他ロードするものはすべて、アプリケーションの2GBウィンドウ内で発生します。
リベース
DLL は、ロードしたい場所を指定します。ベースアドレスがすでに使用されている DLL をロードしようとすると、ロードに失敗するか、DLL をリベースする必要があります。
動作の仕組み
2つの DLL ( DLLs (x.DLL と y.DLL) を持っています。どちらも Visual Studio .NET でコンパイルされています。 Visual Studio では、デフォルトまたは「優先」ベースアドレス(ロードされるメモリ位置)は 0x10000000 です。
- MyTestApp.exe を実行します。
- LoadLibrary(x.DLL);
- LoadLibrary(y.DLL);
x.DLL はにロードされ、 0x10000000;
y.DLL は 0x10000000 にロードしようとしますが、
x.DLL がすでにそのアドレス空間を使っているためロードできません。 そこで、
y.DLL はリベースされます。オペレーティングシステムは、
DLL をロードするために新しい場所を選びます。ロードプロセスの一部では、
y.DLL が 0x10000000 以外の場所で正しく動作するように、オペレーティングシステムが「修正」を適用することが要求されます。
DLL は、その"
好ましい" ベースアドレスでロードされるように最適化されています。 "
fixups" を適用することは、それなりのオーバーヘッドを伴います。優先ベースアドレスを設定すると
DLLs はより速くロードされます。それは、プロセスがロードする他の
DLL の優先ベースアドレスと衝突してはならない。つまり、 ACC がプロセスにインジェクトし、他の何かがすでにインジェクトしている場合、プロセスはクラッシュします。このような事態を防ぐために、
DLL はリベース(他のプロセスに注入)されます。
注: ACC がリベースする
DLL を変更しても、インジェクションが行われないというわけではありません。インジェクションは、スクリプトインタプリタが起動したときに、
SAU/MP/Execution がコマンドライン引数を取得するために必要です。また、インタラクティブモードで実行する場合にも必要です。
特定のプロセスへのインジェクションを明示的に回避したい場合は、
attr -w ルールを追加するか、そのスクリプトインタプリタを
Scripts リストから削除してください。
リベースが定義されているため、
DisableDeviceGuardCompat の設定を変更することで回避できるように見えるかもしれませんが、そうではありません。私たちがやっていることは、別の
DLL をリベースすることです (
LdrLoadDLL をスタックの深いところか高いところにフックして、
kernel32.DLL が
NTDLL.DLL の呼び出しを終了します)。
ホスト側で
DeviceGuardCompat が無効になっており、エンドポイント側で
DeviceGuard が有効になっている場合、オペレーティングシステムはインジェクションを許可しない。バイナリの実行をブロックするのです。
DeviceGuard は、デバイスが許可されていないアプリを実行するのを制限するオペレーティングシステムの機能(ハードウェアおよびソフトウェア)です。
configurable code integrity と呼ばれる機能を使用することで、許可されたアプリの実行を可能にします。
"
DeviceGuardCompat" は、"
Microsoft DeviceGuard" とは
関係ありません。
弊社製品のインジェクションメカニズムは、プロセスがライブラリ (DLL) をロードしているときに検出します。この検出は、
LoadLibrary 関数の RVA を知ることで達成されます。
DisableDeviceGuardCompat 有効な場合、探し出される RVA は
LdrLoadDLL ですが、
NTDLL.DLL の中にあります。逆に、
DisableDeviceGuardCompat が無効(デフォルト)の場合は、Kernel32.DLL の中の
LoadLibraryW を探します。このアドレスを取得した後、特定の関数が呼び出されたときに、インジェクトされたプロセスがドライバーと通信することを許可します。
DisableDeviceGuardCompat は、インジェクトされる
scinject.DLL を無効にしたり、スキップしたりするわけではありません。どの関数がフックされるかを変更するのです。システムを保護することに変わりはないので、インジェクション
DLL を変更することに伴うリスクはありません。