Question

Using the getopt() function in C, it is possible to do that:

program -a arg_for_a -b arg_for_b -c operand1 operand2

and it works with no problem.

But, how to make it work this way?:

program operand1 operand2 -a arg_for_a -b arg_for_b -c

In this case, every argument, including the -a, -b etc. are considered to be operands.

I'm trying to make just like like gcc or ssh does:

gcc code.c -o executable
ssh user@host -i file.pem

That is, no matter in what position the options and the operands come, they are recognized properly.

How to make options be recognized properly wherever they are, and every word that do not follow an option be recognized an operand?

Was it helpful?

Solution

If you use the GNU C library's implementation of getopt, then it will work like all GNU utilities do, because almost all of them use it. In particular, (quoting from man 3 getopt):

By default, getopt() permutes the contents of argv as it scans, so that eventually all the nonoptions are at the end.

That's not quite the same as gcc. gcc cares about the relative order of optional and positional arguments. (For example, it makes a difference where -l goes in the command line.) To do that, you'll have to tell GNU getopt to not permute the arguments. Then, every time getopt reports that it's done, optind will have the index of the next positional argument (if any). You can then use that argument, increment optind, and continue using getopt, which will continue at the next argument.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top