2

メモリ内で自分自身を暗号化/復号化し、.text メモリ領域を実行可能ファイルのコピーに書き込むプログラムを作成しているため、毎回暗号化キーを変更できます。

これは主に、C が苦手なための挑戦であり、アセンブリにもパーツを組み込んでいます。

私のシステムは x86_64 Linux ですが、-m32 でコンパイルしています

-nostartfiles (gcc を使用) も使用しているため、独自の _start 関数を記述できます。この関数はアセンブリで記述されており、.text セクションの残りを復号化/暗号化します。私の問題は、外部関数が間違った順序でコンパイルされていることです。暗号化された後にメモリをダンプしようとすると、暗号化された関数が呼び出されるため、機能しません。

関数の現在の順序は次のとおりです。

  • -static からの一部
  • 正しい順序になっている関数 (アセンブリ関数とメイン C ファイルの関数)
  • -static からもう少し

これは、アセンブリがメインの C ファイルから「下方に」暗号化し、アセンブリ関数から必要ないくつかの -static 関数も暗号化するため、機能しません。

これは、関数を配置したい順序です。

  • すべての -static 関数 & #include <> からのすべて
  • .S アセンブリ ファイルの関数 (.S 全体を順番に)
  • .c メイン ファイルの関数 (.c 全体を順番に)
  • .c メイン ファイルの非標準インクルード (つまり、stdio.h などではなく、#include "" からのもの)

ELF ファイルを手動でマングリングする以外に、必要な関数が暗号化されないようにこれらの関数を並べ替えて、暗号化したい関数を簡単に並べ替える方法はありますか?

musl (代替 libc) でコンパイルするときに編集すると、最初にすべての関数を取得し、残りの静的関数を取得できます。ただし、これはまだ間違った方法です。

4

1 に答える 1

4

バイナリ内の関数の「間違った」順序は、コンパイラの最適化作業に起因します。頻繁に (または頻繁に一緒に) 使用される関数は互いに近くにあるため、呼び出しによってページ フォールトが生成されることはありません。

フラグを使用して、これらの最適化の一部をオフにすることができます-fno-toplevel-reorder。この属性を使用して、関数のサブセットのみを一緒に並べたり (暗号化など)、独自のリンカー スクリプトsectionを記述したりすることもできます。

この質問も参照してください。

于 2013-01-13T12:26:30.693 に答える