valgrind で main 奪う

ことほどさように main は全人類の至宝 LD_PRELOAD をもってしても簡単に奪えないということは、 main 蹂躙厨の間では有名な事実なのですが、 valgrind 使うと割に簡単なことに気付きました。

いつも通り Hello, world を書きます。

#include <stdio.h>
int main() {
    puts("('-') Hello, world!");
}

で実行。

> ./a.out
('-') Hello, world!

平和です。こんな時代が続けば良かったのに!

不審なコードを書きます。

#include <stdio.h>
void _vgrZU_Za_main() {
    puts("('-') ku ku ku ...");
}

主にシンボル名が不審です。さて実行。

> LD_PRELOAD=./hook_main.so valgrind --tool=none -q ./a.out
('-') ku ku ku ...

なんてこった!

えーと valgrind はなんもしない tool であるところの nullgrind (--tool=none で指定) であっても、 _vgrZU_ とかいう謎のプレフィクスではじまってる関数の置換は行なうことになってます。この置換で普段は malloc とか奪ってるわけですね。でこの置換ってのは valgrind の目に入った全てのバイナリに対して行なわれるようなので、 LD_PRELOAD したものでも OK 、と。

_vgrZU_ 以降のフォーマットは、 _vgrZU__ って感じで、 filename の方はエンコードされてます。その法則は valgrind/include/pub_tool_redir.h あたりで。ここではめんどいので Za == アスタリスク == 全てのファイル、を利用してます。

いやこんなことやりたかったんじゃないんだけど。

なにかあれば下記メールアドレスへ。
shinichiro.hamaji _at_ gmail.com
shinichiro.h