ポリモルフィックコードとは、プログラムの本来の機能を保持しつつ、そのコード自体が変異していく技術を指します。主に
コンピュータウイルス、ワーム、
シェルコードなどの悪意あるプログラムが、セキュリティソフトウェアによる検出を逃れるために利用します。
多くの
アンチウイルスソフトウェアや
侵入検知システムは、ファイルやネットワークパケットを検査し、既知の悪意あるコードのパターンとの照合(パターンマッチング)を行います。ポリモルフィックコードは、このパターンマッチングを回避するために、コードを絶えず変化させます。これにより、セキュリティソフトウェアは
マルウェアの特定が困難になります。
ポリモルフィックコードを実現する一般的な手段として、
暗号化が挙げられます。ただし、コード全体を
暗号化してしまうと実行できなくなるため、一部のコードは
暗号化せずに残す必要があります。
アンチウイルスソフトウェアは、この
暗号化されていない部分を標的として検出を試みます。そのため、
マルウェア作成者は、復号エンジン部分をプログラムが伝播するたびに書き換えることで、検出を回避しようとします。一方、
アンチウイルスソフトウェアは、復号エンジンの変異にも影響されないパターンを探索し、
マルウェアの検出精度向上を目指します。
世界で初めてポリモルフィックコードを用いたウイルスを作成したのは、Mark Washburnです。彼の作成したウイルス「1260」は1990年に登場しました。その後、1992年には、
ブルガリアのクラッカーであるDark Avengerが、ミューテーションエンジン「DAME」(または「MtE」)を作成しました。MtEは、他のウイルスに寄生し、そのコードを
暗号化する「エンジン」であり、自身は厳密にはウイルスではありません。このMtEの登場は、ポリモルフィックコードの普及に大きな影響を与えました。
ポリモルフィックコードの具体的な例
以下は、
暗号化されたコードを復号して実行する
擬似コードの例です。
Start:
GOTO Decryption_Code
Encrypted:
...
暗号化されたコード列 ...
Decryption_Code:
A = Encrypted
Loop:
B = A
B = B XOR CryptoKey
A = B
A = A + 1
GOTO Loop IF NOT A = Decryption_Code
GOTO Encrypted
CryptoKey:
何らかの乱数
上記のコードでは、`Encrypted`部分が
暗号化されており、`Decryption_Code`で復号されます。`CryptoKey`は
暗号化・復号に使用される鍵です。このコードを擬装するために、例えば以下のように、不要な変数を導入することも可能です。
Start:
GOTO Decryption_Code
Encrypted:
...
暗号化されたコード列 ...
Decryption_Code:
C = C + 1
A = Encrypted
Loop:
B = A
C = 3214 A
B = B XOR CryptoKey
A = B
C = 1
C = A + B
A = A + 1
GOTO Loop IF NOT A = Decryption_Code
C = C^2
GOTO Encrypted
CryptoKey:
何らかの乱数
この例では、変数`C`を操作するコードを追加して、コードの構造を変化させています。また、
暗号化キーは最初はゼロ(何も変化しない状態)で開始し、実行中に新たな
暗号キーを生成することで、コードを
暗号化する方法も存在します。
その他にも、NOP(何もしない)命令を挿入するなど、様々なポリモルフィックな技法が存在します。
関連技術
自己書き換えコード: 実行時に自身のコードを書き換える技術。
シェルコード: 特定の動作を行うための小さなコード。
クラッキング (コンピュータ): コンピュータシステムへの不正侵入やその手法。
参考文献
* Diomidis Spinellis. Reliable identification of bounded-length viruses is NP-complete. IEEE Transactions on Information Theory, 49(1):280–284, January 2003. doi:10.1109/TIT.2002.806137