Lucky for us, such a mechanism does exist; namely the Popt library.
Start by installing the Popt package:
$ sudo apt-get install libpopt-dev
A short example of an application which uses the library follows:
1 #include <popt.h>
2 #include <stdio.h>
3 #include <stdlib.h>
4
5 int main(int argc, char **argv) {
6 /* option parsing variables */
7 char ch;
8 poptContext opt_con; /* context for parsing command-line options */
9 char *extra_arg;
10 static int i=0;
11 static char *s="";
12 static float f=0.0;
13 static double d=0.0;
14 int verbose=0;
15
16 static struct poptOption options_table[] = {
17 { "integer", 'i', POPT_ARG_INT, &i, 'i', "grab an integer", "INT" },
18 { "string", 's', POPT_ARG_STRING, &s, 's', "grab a string", "STRING" },
19 { "float", 'f', POPT_ARG_FLOAT, &f, 'f', "grab a float", "FLOAT" },
20 { "double", 'd', POPT_ARG_DOUBLE, &d, 'd', "grab a double", "DOUBLE" },
21 { "verbose", 'v', POPT_ARG_NONE, NULL, 'v', "enable verbose", "" },
22 POPT_AUTOHELP
23 { NULL, 0, 0, NULL, 0 } /* end-of-list terminator */
24 };
25
26 opt_con = poptGetContext(NULL, argc, (const char **)argv, options_table, 0);
27
28 /* Now do options processing */
29 while ((ch = poptGetNextOpt(opt_con)) >= 0) {
30 printf("between while & switch: ch = %c\n", ch);
31 switch (ch) {
32 case 'i':
33 printf("handling 'i' option.\n");
34 break;
35 case 's':
36 printf("handling 's' option.\n");
37 break;
38 case 'f':
39 printf("handling 'f' option.\n");
40 break;
41 case 'd':
42 printf("handling 'd' option.\n");
43 break;
44 case 'v':
45 printf("handling 'v' option.\n");
46 verbose = 1;
47 break;
48 }
49 }
50
51 if (ch < -1) {
52 // the user specified an invalid option, tell them
53 poptPrintHelp(opt_con, stderr, 0);
54 }
55
56 /* non-option args */
57 while (extra_arg = (char *)poptGetArg(opt_con)) {
58 printf("extra arg: %s\n", extra_arg);
59 exit(1);
60 }
61
62
63 /* cleanup */
64 poptFreeContext(opt_con);
65
66 printf("(%s:%d) i = %d\n",__FILE__,__LINE__,i);
67 printf("(%s:%d) s = '%s'\n",__FILE__,__LINE__,s);
68 printf("(%s:%d) f = %f\n",__FILE__,__LINE__,f);
69 printf("(%s:%d) d = %lf\n",__FILE__,__LINE__,d);
70 printf("(%s:%d) v = %d\n",__FILE__,__LINE__,verbose);
71
72
73 return EXIT_SUCCESS;
74 }
You compile and link the application by:
g++ -Wall main.o -lpopt -o main
An added bonus of using this application is the automatic introduced interfaces for a brief and more verbose help descriptions.
~/Desktop/sourceCode/C/popt$ ./main --help
Usage: main [OPTION...]
-i, --integer=INT grab an integer
-s, --string=STRING grab a string
-f, --float=FLOAT grab a float
-d, --double=DOUBLE grab a double
-v, --verbose enable verbose
Help options:
-?, --help Show this help message
--usage Display brief usage message
~/Desktop/sourceCode/C/popt$ ./main --usage
Usage: main [-v?] [-i|--integer INT] [-s|--string STRING] [-f|--float FLOAT]
[-d|--double DOUBLE] [-v|--verbose] [-?|--help] [--usage]
The heart of the library lies with proper initialization of the popt structure which is defined as follows:
struct poptOption {
const char * longName;
char shortName;
int argInfo;
void * arg;
int val;
const char * descrip;
const char * argDescrip;
};
The ability to specify either a long or short argument name is common practice; -h or --help is a common example of this form.The long and short forms are specified as the 1st and 2nd element in the popt structure. The 3rd and 4th specify of what type the following argument consists of as well as the address in which the value will be stored. The 6th and 7th arguments specify the argument description and argument field name which is displayed in the help and brief. The 5th field is a bit of a mystery at this time.
That's all for now.
No comments:
Post a Comment