そして、プログラム自体が必要のないアクションを知っていて、念のためにそれらをオフにすると良いでしょう。
アンチウイルスおよびその他の類似システムは、防御者の役割を引き受けようとしますが、すべての保護は、多くの人にとって同じルールのセットになり、保護されたプログラムの仕様を考慮しません。 このアプローチは、不快な状況につながることがあります。 以下に例を示します。
- ブラウザに悪意のあるコードを導入-ネットワーク機能への妨害されないアクセスを取得します。
- メールプログラムに埋め込まれた悪意のあるコード-ウイルス対策がこれらのファイルを保護するという事実にもかかわらず、メールデータベースファイルへの妨害されないアクセスを取得します。
- ネットワークプログラムの脆弱性を悪用する-ユーザーが最小限の権限しか持っていないにもかかわらず、システムにアクセスしたり、権限を増やしたりできる場合があります。
しかし、前述のように、プログラムの作者は自分のプログラムが何をすべきかを最もよく知っています。 それでは、特定のアクションに制限をかける機会を彼に与えてみませんか? プログラム全体ではなく、特定のスレッド用です。
アイデアの生産性
これにより、以下を達成できます。
- 情報処理と視覚化のフローはネットワークで機能しませんでした。
- ネットワークワークフローは、別のプログラムを実行することも、他のプロセスに埋め込むこともできませんでした。
- プログラムに埋め込まれた悪意のあるコードは、ウイルス対策ソフトウェアとの信頼レベルを利用できませんでした。
より現実的な点から言えば、次のことができます。
- ブラウザ自体がサードパーティのプログラムの起動を禁止する可能性があります。
- メールプログラムはデータベースファイルにアクセスできましたが、それに埋め込まれたコードはアクセスできませんでした。
- どのプログラムでも、その異常な活動について知ることができます。
アイデアの実装と使用の機能
このアイデアを実装するには、Windowsカーネルで次のことが必要です。
- 2つのシステム構造を編集します。
- 1つのシステムコールを追加します。
- 50〜100行でコードを記述します。
kernel32.dllに、保護を制御する関数を1つ追加します。 これも特に大きくはありません。
これらのアクションは、プログラマーの力の範囲内です(1日で)。 しかし、最大の困難は、Microsoft自身がこれを行わなければならないことです。 そのため、このような防御メカニズムは今のところ夢の中に残っています。
理論的後退
ユーザーモードの制限は簡単に回避または削除できるため、カーネルにすべての保護を実装する必要があります。
Windowsでシステム関数を呼び出す基本原則は、次の図のように表すことができます。

sysenter / syscall / int 0x2Eを呼び出すか、dword ptr fs:[0xC0](windowsのバージョンによって異なります)を呼び出した後、制御はカーネルに移動し、KiSystemService関数はシステムサービスアドレス(SDT)のテーブルとeaxレジスタに渡されたサービス番号を調べます)目的の機能のアドレスを見つけて、制御を転送します。 したがって、目的の関数が呼び出されます。
システムは2つのテーブルを使用します。1つはシステムの操作を直接担当し、カーネルが処理し、2つ目はGUIの操作を担当し、win32.sysドライバが処理します。 最初の表に興味があります。
このアーキテクチャのおかげで、システム機能の呼び出しにアクセス制限をかけることができます。 これを行うには、単純なチェックをKiSystemService関数に挿入するだけです。
私たちはすでに検証の場所を見つけました、今では
Windowsオペレーティングシステムでは、カーネルはKTHREAD構造を使用してストリームを記述します。各ストリームには独自のストリームがあります。 これは、アクセスマトリックスを格納できる場所です。 しかし、今ではマトリックスではなく、線形リストになります(各スレッドはそれ自体に関する情報のみを保存するため)。
すべてがうまくいきますが、ネットワークもあり、その作業は特別なドライバーを介して行われます。 ただし、ここでは、デバイス\\ Device \ Tcp、\\ Device \ Udp、\\ Device \ RawへのIRP要求を処理することで問題が解決されます。これにより、特定のストリームからネットワークにアクセスする機能を透過的に確認できます。
保護の実装方法
保護の実装は次のとおりです。
- 各ストリームの記述構造には、ビットで構成される禁止の表があります。 Windows 7では、SDTには360個の関数があるため、屋根の上には512ビット(64バイト)の配列で十分です。
- デフォルトでは、すべてのビットがリセットされます(つまり、禁止はありません)
- 64ビットキーフィールドもありますが、これについては後で説明します。
- 関数のコールバックアドレスを格納する32/64ビットフィールドもあります
- 76/80バイトのデータがある合計
- 別のシステムコールがカーネルに追加され、次の規則に従って構造を埋めます。
- ビットはいつでも設定できます。
- ビットをリセットするには、特別なセキュリティキーを指定する必要があります。
- 特別なキーは一度しか取得できません。
- コールバック機能は、キーを使用して1回または無制限に設定できます。
- kernel32.dllおよびntdll.dllに、保護管理を整理するシステムコールにインターフェイス関数が追加されました。
保護の進捗状況:
- KiSystemServiceまたはネットワークドライバーのIRP要求ドライバーで、PTHREAD構造体へのポインターを取得します。
- インデックスの境界を確認します(SDTの数値の場合)
- ビットが設定されているかどうかを確認します。 設定されている場合、STATUS_ACCESS_DENIEDを返します
- ビットが設定され、コールバック関数が指定されている場合、それを呼び出します。 したがって、あるスレッドが禁止されたアクションを実行しようとしたことをプロセスに通知します。
保護をインストールする機能に特に注意を払いたいです。 彼女のプロトタイプは次のように見えます:
DWORD QuerySystemSecurity(ハンドルhThread、DWORDフラグ、QWORD *キー、無効*データ);
- hThread-保護が設定されているスレッドへのハンドル。 または、現在のスレッドの場合は0xFFFFFFFF。
- フラグ -通過または要求されたパラメーター:
- キーを取得します。
- 機能の禁止を設定します。
- 機能のリストに禁止を設定します。
- 機能グループに禁止を設定します。 -たとえば、ファイルまたはプロセスの操作。
- コールバック関数を設定します。
- 機能の禁止を解除します。
- 保護テーブルを継承するかどうか。
- キーが指定されている場合でも、削除保護を拒否します。
- キーの受け取りを拒否します。
- キー - キーのアドレスまたはNULL。
- データ -フラグに応じたデータ。
また、QuerySystemSecurityには、禁止されている機能の番号とSDTからのその番号への対応表が必要です。 後者はバージョンごとに異なります。
おわりに
1つの単純な機能とカーネルのわずかな変更により、非常に柔軟で高速な保護を実現できます。 プログラマー自身は、プログラムに対する異常なアクションを禁止することができます。 これは、ネットワークプログラムおよび主にブラウザで非常に役立ちます。
このアプローチに基づく保護により、プログラム内のサードパーティコードの実行をより柔軟に制御できるようになります(悪意があるだけでなく、他の作成者からのプラグインも)。 プログラムの小規模な開発者がこのような保護に関心を持たない場合、大規模な開発者はそれを簡単に使用して、他の人のコードの介入からプログラムの保護を強化できます。
もちろん、このような保護はMicrosoft自体だけでなく、サードパーティの開発者によっても実装できますが、すでに松葉杖であり、(PTHREADにデータを保存することを拒否する必要があるため)効率的に機能せず、そのようなグローバルな規模はありません。
しかし、いつものように、これらは保護の存在についてのあなた自身の夢であり、マイクロソフトはほとんど気付かないでしょう。