views:

140

answers:

6

I've read the first array member of argv will always be the program name.

Is it ever useful to hang on to this? I'm learning, so forgive me please if it is a dumb question.

Do people ever unshift the first member because it is useless (and reset argv to be one less?), or is leaving it there best practice because people expect it will always be there (and for it to work out of the box with argc) ?

+3  A: 

To be precise, argv[0] is whatever is passed to exec(2) which is conventionally the program name but could be anything.

Don't unshift it because too many hidden dependencies count on it.

msw
Hidden dependencies? There is no function `exec`. There is `execve(2)` but it and its family requires the new file name as an argument. Why would you `execl` the current executable? That would just reinitialize everything.
Potatoswatter
+7  A: 

I've read the first array member of argv will always be the program name.

It should be. C and C++ both require that if argc is greater than zero, argv[0] shall either be the program name or an empty string.

Some systems do not necessarily follow this convention in all circumstances (on Windows, for example, you can use CreateProcess to create a new process and not pass the program name in the command line arguments that are used to populate argc and argv).

Is it ever useful to hang on to this?

Sure. If you want to spawn another instance of yourself, for example, or if you want to print your program name (for example in usage instructions).

Do people ever unshift the first member because it is useless, or is leaving it there best practice?

Don't change the actual arguments; the next person who comes along will probably be expecting them to be in their original form.

James McNellis
for the next person! :D
Nyan
The Unix `exec()` family of system calls also allow `argv[0]` to be specified independently of the file to exit. The login shell, for instance, usually has a leading `-` attached to its name by the login process using this feature.
RBerteig
+3  A: 

It is expected that argv[0] will always contain the name of the executable. Because of this you should never remove it.

As for whether it's useful, one use for argv[0] is if you want your application to change behaviour based on how it was called.

Busybox, for example, makes use of this on embedded linux systems. Typically you would have a single copy of the executable and create symbolic links to the executable with different names. eg. cp, rm, ls, etc. Busybox then determines which function to perform based on the contents of argv[0].

Andrew Edgecombe
Sounds interesting, however, is that a standard thing to do or is it limited to the Busybox application?
alex
It's a pretty standard technique. Also used in applications like ccache and distcc.
Andrew Edgecombe
IIRC, Many of the core "two letter" utilities were implemented the same way on System III and early BSD releases. (Am I showing my age here by admitting to having *used* System III?)
RBerteig
I don't believe this is a good general argument. These are all shell-like applications (or, in Sys III, the actual shell). You know before you start a project whether it will emulate the command-line behavior of other programs.
Potatoswatter
+3  A: 

The first argument isn't always the program name - it depends on how it's called (see here).

Often, argv[0] is used in help text:

fprintf(stderr, "Usage: %s <foo> [bar]\n", argv[0]);

Shifting the array isn't terribly useful or efficient. You may as well just start using argv from index 1.

sje397
@caf: ty 4 the edit :)
sje397
`++ argv; -- argc;` efficiently shifts the array. I think that's what OP means.
Potatoswatter
A: 

contents of argv[0] is not defined by ANSI. argv can enumerated:

main(int argc,char**argv)
{
  while( argc-- )
    puts(*argv++);
  return 0;
}
A: 

From ISO C99, §5.1.2.2.1,

If the value of argc is greater than zero, the string pointed to by argv[0] represents the program name; argv[0][0] shall be the null character if the program name is not available from the host environment.

Therefore, on conforming implementations, you can rely on argv[0] as being the program's name if you test for it's existence before (that is, if you can assert that argc > 0).

Alek