[迷信] argv[0] はプログラム名

main 関数が argc と argv の二つの仮引数を受け取る場合、argv[0] がプログラム名を表す文字列を指すというのは入門書にも載っています。しかし、常にそうかというと、「そうではない」としかいえなくなります。今回はフリースタンディング環境の話は除外して、ホスト環境の話に限って、この部分の事実関係がどうなっているかをご紹介します。

argv[0] がプログラム名にならないケースは、大きく分けて二つあります。ひとつは、そのそも main 関数にプログラム名が渡されないケースがある場合であり、もうひとつは、ユーザープログラムから main 関数を呼び出した場合です。

まずは、そもそも main 関数にプログラム名が渡されないケースについて見ていきます。JIS X3010:2003 の 5.1.2.2.1 プログラム開始処理から引用すると...

 二つの仮引数を定義する場合,関数 main の仮引数は,次の制約に従わなければならない。
- argc の値は,非負でなければならない。
- argv[argc]は,空ポインタでなければならない。
(中略)
- argc の値が正の場合,argv[0] が指す文字列は,プログラム名(program name)を表す。ホスト環境からプログラム名を得ることができない場合,argv[0][0] は,ナル文字でなければならない。

上記は C の規格ですが、C++ の規格である JIS X3014:2003 でも(表現は違いますが)同等のことが規定されています。これからも分かるように,argc が 0 の場合には argv[0](すなわち argv[argc])は空ポインタ(=NULL)でなければなりませんので,プログラム名ではないことになります。このような処理系は実在します。また,argc > 0 であっても,プログラム名が得られない場合は argv[0] が "" を指すことになります(このようになる具体的な処理系は知りませんが...)。

次に,ユーザープログラムから main 関数を呼び出す場合です。これは C だけで可能なことであって、C++ では main 関数を直接呼び出すことも、関数へのポインタを介して間接的に呼び出すこともできません。ですので、以下は C に限った話になります。

ユーザープログラムから main 関数を呼び出す場合、それこそ実引数にどんなものを渡すかはプログラムの作り方次第になります。argc に負の値を渡すことも、argv に空ポインタを渡すこともできてしまいます。ですので、argv[0] がプログラム名になるかどうかも、完全にユーザープログラムの作り方次第になるわけです。

この記事のトラックバックURL:

http://www.kijineko.co.jp/trackback/620
このエントリーを含むはてなブックマーク