特権の昇格を行うときに、SUIDが設定されたアプリケーションとデバッガーを想定すると、デバッガー内からシェルを起動できなくなりますか?シェルコードを環境変数またはメモリ内のどこかに記述し、デバッガー内からポインターを呼び出すだけです。または、いずれの場合も、それが機能しない場合は、スタックの戻りアドレスを手動で変更し、場合によっては後で切り離すこともできます。
何かが足りないと思いますが、それがよくわかりません。私の推測では、デバッガーが接続されるとSUIDビットがクリアされます。それ以外の場合、これは特権を昇格させる非常に一般的な方法です。
デバッガー内からシェルを起動できない理由は何ですか?
デバッガーでsetuidプログラムを実行し、rootでない場合は、setuidしていない場合と同じように実行されます。つまり、ルートではなく、IDの下で実行されます。したがって、シェルを生成することはできますが、それはあなたの資格情報を使用します。
自分で簡単にテストするには、gdbでsuを起動し、別のコンソールでユーザーアカウントで実行されていることを確認します。
また、setuidプログラムを起動してから、gdbをアタッチしようとすると、「許可が拒否されました」というエラーが返されます。
昇格された特権でプロセスに接続できるのはrootだけです。もう少し詳しく説明すると、 ptrace システムコール(デバッガーが内部で使用するもの)を使用して実行中のプロセスにアタッチするには、いくつかの条件が必要です。古典的なUnixの条件である必要条件は、ターゲットプロセスが昇格された特権なしで実行されている場合(setuid、setgid、setcapなどの他の特権昇格メカニズムがない場合)、ptrace
を呼び出すプロセスは同じユーザーIDで実行されています。 root(実効ユーザーIDが0)として実行されているプロセスは常に接続できるため、rootは任意のプロセスをデバッグできます。
(Linuxはその硬化状態に応じて追加の制限があります。ほとんどのディストリビューションはkernel.yama.ptrace_scope
to1。これにより、any非ルートプロセスがその子プロセスのトレースを除いてptrace
を実行できなくなります。つまり、デバッガーでプログラムを実行できますが、既に実行中のプロセスにデバッガーをアタッチすることはできません。)
さらに、プロセスがトレースされている(つまり、デバッグされている)場合、その特権を昇格することはできません。権限の昇格は、実行されたファイルの権限フラグに基づいて、execve
システムコールによって実行されます。トレース中にプロセスがexecve
を呼び出すと、特権昇格フラグは無視され、新しいプロセスイメージはexecve
を呼び出す前と同じ特権を持ちます。
このように、特権の昇格は、セキュリティへの影響を変更する可能性があるものと互換性がありません。 rootとしてデバッガーを実行しない限り、追加の特権を使用してプロセスでデバッガーを実行するように調整する方法はありません(実行できる場合は、まだ持っていない特権を取得できません)。
昇格された特権で実行されるプログラムをデバッグする場合、2つの方法があり、どちらもデバッガーをrootとして実行する必要があります。デバッガーを起動して、プロセスの実行に使用する特権を設定する準備コード全体を実行させることができます。または、プログラムを通常の状態で起動させ、いつでもデバッガーをプログラムに接続できます。
もちろん、プログラムがsetuidとして開始し、次に特権を削除する場合(つまり、実効ID、実ユーザー、および保存済みのユーザーIDが等しくなり、同様にグループIDと他の特権が存在する場合)、同じユーザーで実行しているデバッガーをアタッチした後、プロセスはその特権を落としました。