PHP界きっての反則技、runkit。
http://www.php.net/manual/ja/book.runkit.php
昔はXAMPPにデフォルトで入っていたのですが、いつのまにか消えていました。
http://yuubiseiharukana.blog.shinobi.jp/Entry/75/
もはやPECLがメンテナンスされてないんですよね。
http://pecl.php.net/package/runkit
Windows版runkitをメンテしてる人を見つけたので試してみます。
https://github.com/Crack/runkit-windows
試したバージョンは「php_runkit-1.0.4-5e179e978a-5.5-vc11.dll」。
TSのほうです。
ダウンロードしたファイルをxampp/php/ext内に入れて、php.iniに
extension=php_runkit.dll
runkit.internal_override = true
runkit.superglobal = _FOO
と書いておきます。
phpinfo()でrunkitの項目が追加されていることを確認しましょう。
runkitを使うと、通常では絶対に有り得ないコーディングが可能になります。
<?php
// 定数
define('HOGE', 1);
print(HOGE); // 1
runkit_constant_redefine('HOGE', 2);
print(HOGE); // 2
runkit_constant_remove('HOGE');
print(HOGE); // Notice: Use of undefined constant HOGE
// 関数
runkit_function_redefine('phpinfo', null, 'print("a");');
phpinfo(); // "a"と表示される
runkit_function_remove('phpinfo');
phpinfo(); // Call to undefined function phpinfo()
// 返り値を利用しているか確認
function foo() {
var_dump(runkit_return_value_used());
}
foo(); // false
$a = foo(); // true
// スーパーグローバル
$_FOO = 'foo';
$_BAR = 'bar';
function test(){
print($_FOO); // foo
print($_BAR); // Notice: Undefined variable: _BAR
}
test();
var_dump(runkit_superglobals());
掟破りにも程があるだろ。
見てのとおり、定数も関数も制限?何それってレベルで上書きできてしまいます。
runkit.internal_overrideは組み込み関数のオーバーライドを制御するディレクティブです。
デフォルトはfalseで、ユーザ定義関数しか上書きできません。
trueにすると上記のようにphpinfo()等も上書きできるようになります。
さすがにechoのような言語構造は上書きできません。
runkit.superglobalは、「スーパーグローバル変数として扱う変数を追加する」というこれまた反則なディレクティブです。
今回は"_FOO"を追加しているので、$_FOOが$_REQUEST等と同格のスーパーグローバル変数になります。
runkit_superglobals()は、現在のスーパーグローバル変数一覧を取得します。
$GLOBALS、$_REQUEST、$_SESSIONといった見慣れた変数と一緒に$_FOOが入っているのが確認できます。
runkit_return_value_used()は他と毛色の違う関数で、関数呼び出しが、その返り値を使っているかを確認できるという、どういうときに使うのかよくわからない機能です。
いやほんとこれどういうときに使うんだ?
あとrunkit_lint()でコードチェックとかも可能なはずなのですが、手元環境ではapache毎落ちてしまって確認できませんでした。
理由はよくわかりません。