Re: [RFC] git-fsck-cache argument processing
- From
- Jeff Garzik <jgarzik@pobox.com>
- Date
- May 21, 2005, 04:08 UTC
- Message-ID
- <428EB444.7010200@pobox.com>
- In-Reply-To
- <4870.10.10.10.24.1116646732.squirrel@linux1>
Sean wrote:
Show 8 quoted lines
> Here is a first crack at using argp as suggested by Jeff Garzik to > implement argument processing as requested by Junio and Linus. Each of > the long arguments have been given a single character equivalent as well. > > This patch only converts fsck-cache to use argp in case anyone has > objections to the basic format or style. The patch includes a version > number inside of fsck-cache.c; this should really be in a separate include > file so you can run any command with --version and get the same answer.
Pretty good. You'll probably want some additional changes:
1) eliminate + case ARGP_KEY_ARG: state->next = state->argc; break;
This will cause option processing to stop at the first unknown argument.
2) Pass-by-reference a variable to argp_parse(), which will store the index of the argument where processing stopped. This is the first hash/file/etc. non-option argument.
(example code from posixutils)
int parse_cmdline(struct cmdline_walker *cw)
{
error_t rc_argp;
int idx = 0; rc_argp = argp_parse(cw->argp, cw->argc, cw->argv, 0, &idx, NULL);
if (rc_argp) {
fprintf(stderr, "argp_parse: %s\n", strerror(rc_argp));
return -rc_argp;
}return idx; }
'idx' in this case is the first non-option argument, which can be passed directly to argv[]. From there, you perform standard iteration over the arguments provided on the command line, starting at argv[idx].
If you have a fixed number of arguments following the options, then your parse_opt function can easily parse those args as well:
static error_t parse_opt (int key, char *arg, struct argp_state *state)
{
switch (key) {
case '1':
outmask |= OPT_FILE1;
break;
case '2':
outmask |= OPT_FILE2;
break;
case '3':
outmask |= OPT_DUP;
break; case ARGP_KEY_ARG:
switch(state->arg_num) {
case 0: file1 = arg; break; /* 1st non-opt arg */
case 1: file2 = arg; break; /* 2nd non-opt arg */
default: argp_usage (state); break; /* too many args */
}
break; case ARGP_KEY_END:
if (state->arg_num < 2) /* not enough args */
argp_usage (state);
break; default:
return ARGP_ERR_UNKNOWN;
}return 0; }