2013年1月9日水曜日

perl の eval 〜 if 0 ってなんだ?

perl で書かれたスクリプトの先頭によくある、以下のようなもの。
最初、いったいなんだろう?と思った。
#! /usr/bin/perl -w

eval 'case $# in 0) exec /usr/bin/perl -S "$0";; *) exec /usr/bin/perl -S "$0" "$@";; esac'
    if 0;
ここでの eval というのは perl の関数ではなくて、シェルのコマンドであるというのがポイント。
どうもこれは #! を解釈してくれないような環境用の回避策らしい。

もし、このスクリプトが perl で実行されているのなら、
〜 if 0; という形なので(後置のif)
eval 'case $# in 0) exec /usr/bin/perl -S "$0";; *) exec /usr/bin/perl -S "$0" "$@";; esac'
の部分はまるまる無視され、何も起きない。そのまま残りのスクリプトを実行します。

一方、このスクリプトがシェルで実行されているのなら、
eval 'case $# in 0) exec /usr/bin/perl -S "$0";; *) exec /usr/bin/perl -S "$0" "$@";; esac'
がシェルによって実行されて、 /usr/bin/perl でこのスクリプトを実行し直すことになる。
    if 0;
にはたどり着きません。

perl の文は「;」区切り、シェルスクリプトは「改行」区切りというのをうまく利用しています。
よくもまあこんなことを考えた人がいたもんだ。

0 件のコメント:

コメントを投稿