|
Packit |
f00812 |
/* flex - tool to generate fast lexical analyzers */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Copyright (c) 1990 The Regents of the University of California. */
|
|
Packit |
f00812 |
/* All rights reserved. */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* This code is derived from software contributed to Berkeley by */
|
|
Packit |
f00812 |
/* Vern Paxson. */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* The United States Government has rights in this work pursuant */
|
|
Packit |
f00812 |
/* to contract no. DE-AC03-76SF00098 between the United States */
|
|
Packit |
f00812 |
/* Department of Energy and the University of California. */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* This file is part of flex. */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Redistribution and use in source and binary forms, with or without */
|
|
Packit |
f00812 |
/* modification, are permitted provided that the following conditions */
|
|
Packit |
f00812 |
/* are met: */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* 1. Redistributions of source code must retain the above copyright */
|
|
Packit |
f00812 |
/* notice, this list of conditions and the following disclaimer. */
|
|
Packit |
f00812 |
/* 2. Redistributions in binary form must reproduce the above copyright */
|
|
Packit |
f00812 |
/* notice, this list of conditions and the following disclaimer in the */
|
|
Packit |
f00812 |
/* documentation and/or other materials provided with the distribution. */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Neither the name of the University nor the names of its contributors */
|
|
Packit |
f00812 |
/* may be used to endorse or promote products derived from this software */
|
|
Packit |
f00812 |
/* without specific prior written permission. */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR */
|
|
Packit |
f00812 |
/* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED */
|
|
Packit |
f00812 |
/* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR */
|
|
Packit |
f00812 |
/* PURPOSE. */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
#include "flexdef.h"
|
|
Packit |
f00812 |
#include "scanopt.h"
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Internal structures */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
#define ARG_NONE 0x01
|
|
Packit |
f00812 |
#define ARG_REQ 0x02
|
|
Packit |
f00812 |
#define ARG_OPT 0x04
|
|
Packit |
f00812 |
#define IS_LONG 0x08
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
struct _aux {
|
|
Packit |
f00812 |
int flags; /* The above hex flags. */
|
|
Packit |
f00812 |
int namelen; /* Length of the actual option word, e.g., "--file[=foo]" is 4 */
|
|
Packit |
f00812 |
int printlen; /* Length of entire string, e.g., "--file[=foo]" is 12 */
|
|
Packit |
f00812 |
};
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
struct _scanopt_t {
|
|
Packit |
f00812 |
const optspec_t *options; /* List of options. */
|
|
Packit |
f00812 |
struct _aux *aux; /* Auxiliary data about options. */
|
|
Packit |
f00812 |
int optc; /* Number of options. */
|
|
Packit |
f00812 |
int argc; /* Number of args. */
|
|
Packit |
f00812 |
char **argv; /* Array of strings. */
|
|
Packit |
f00812 |
int index; /* Used as: argv[index][subscript]. */
|
|
Packit |
f00812 |
int subscript;
|
|
Packit |
f00812 |
char no_err_msg; /* If true, do not print errors. */
|
|
Packit |
f00812 |
char has_long;
|
|
Packit |
f00812 |
char has_short;
|
|
Packit |
f00812 |
};
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Accessor functions. These WOULD be one-liners, but portability calls. */
|
|
Packit |
f00812 |
static const char *NAME(struct _scanopt_t *, int);
|
|
Packit |
f00812 |
static int PRINTLEN(struct _scanopt_t *, int);
|
|
Packit |
f00812 |
static int RVAL(struct _scanopt_t *, int);
|
|
Packit |
f00812 |
static int FLAGS(struct _scanopt_t *, int);
|
|
Packit |
f00812 |
static const char *DESC(struct _scanopt_t *, int);
|
|
Packit |
f00812 |
static int scanopt_err(struct _scanopt_t *, int, int);
|
|
Packit |
f00812 |
static int matchlongopt(char *, char **, int *, char **, int *);
|
|
Packit |
f00812 |
static int find_opt(struct _scanopt_t *, int, char *, int, int *, int *opt_offset);
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
static const char *NAME (struct _scanopt_t *s, int i)
|
|
Packit |
f00812 |
{
|
|
Packit |
f00812 |
return s->options[i].opt_fmt +
|
|
Packit |
f00812 |
((s->aux[i].flags & IS_LONG) ? 2 : 1);
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
static int PRINTLEN (struct _scanopt_t *s, int i)
|
|
Packit |
f00812 |
{
|
|
Packit |
f00812 |
return s->aux[i].printlen;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
static int RVAL (struct _scanopt_t *s, int i)
|
|
Packit |
f00812 |
{
|
|
Packit |
f00812 |
return s->options[i].r_val;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
static int FLAGS (struct _scanopt_t *s, int i)
|
|
Packit |
f00812 |
{
|
|
Packit |
f00812 |
return s->aux[i].flags;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
static const char *DESC (struct _scanopt_t *s, int i)
|
|
Packit |
f00812 |
{
|
|
Packit |
f00812 |
return s->options[i].desc ? s->options[i].desc : "";
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
#ifndef NO_SCANOPT_USAGE
|
|
Packit |
f00812 |
static int get_cols (void);
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
static int get_cols (void)
|
|
Packit |
f00812 |
{
|
|
Packit |
f00812 |
char *env;
|
|
Packit |
f00812 |
int cols = 80; /* default */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
#ifdef HAVE_NCURSES_H
|
|
Packit |
f00812 |
initscr ();
|
|
Packit |
f00812 |
endwin ();
|
|
Packit |
f00812 |
if (COLS > 0)
|
|
Packit |
f00812 |
return COLS;
|
|
Packit |
f00812 |
#endif
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if ((env = getenv ("COLUMNS")) != NULL)
|
|
Packit |
f00812 |
cols = atoi (env);
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
return cols;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
#endif
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Macro to check for NULL before assigning a value. */
|
|
Packit |
f00812 |
#define SAFE_ASSIGN(ptr,val) \
|
|
Packit |
f00812 |
do{ \
|
|
Packit |
f00812 |
if((ptr)!=NULL) \
|
|
Packit |
f00812 |
*(ptr) = val; \
|
|
Packit |
f00812 |
}while(0)
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Macro to assure we reset subscript whenever we adjust s->index.*/
|
|
Packit |
f00812 |
#define INC_INDEX(s,n) \
|
|
Packit |
f00812 |
do{ \
|
|
Packit |
f00812 |
(s)->index += (n); \
|
|
Packit |
f00812 |
(s)->subscript= 0; \
|
|
Packit |
f00812 |
}while(0)
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
scanopt_t *scanopt_init (const optspec_t *options, int argc, char **argv, int flags)
|
|
Packit |
f00812 |
{
|
|
Packit |
f00812 |
int i;
|
|
Packit |
f00812 |
struct _scanopt_t *s;
|
|
Packit |
f00812 |
s = malloc(sizeof (struct _scanopt_t));
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
s->options = options;
|
|
Packit |
f00812 |
s->optc = 0;
|
|
Packit |
f00812 |
s->argc = argc;
|
|
Packit |
f00812 |
s->argv = (char **) argv;
|
|
Packit |
f00812 |
s->index = 1;
|
|
Packit |
f00812 |
s->subscript = 0;
|
|
Packit |
f00812 |
s->no_err_msg = (flags & SCANOPT_NO_ERR_MSG);
|
|
Packit |
f00812 |
s->has_long = 0;
|
|
Packit |
f00812 |
s->has_short = 0;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Determine option count. (Find entry with all zeros). */
|
|
Packit |
f00812 |
s->optc = 0;
|
|
Packit |
f00812 |
while (options[s->optc].opt_fmt
|
|
Packit |
f00812 |
|| options[s->optc].r_val || options[s->optc].desc)
|
|
Packit |
f00812 |
s->optc++;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Build auxiliary data */
|
|
Packit |
f00812 |
s->aux = malloc((size_t) s->optc * sizeof (struct _aux));
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
for (i = 0; i < s->optc; i++) {
|
|
Packit |
f00812 |
const unsigned char *p, *pname;
|
|
Packit |
f00812 |
const struct optspec_t *opt;
|
|
Packit |
f00812 |
struct _aux *aux;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
opt = s->options + i;
|
|
Packit |
f00812 |
aux = s->aux + i;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
aux->flags = ARG_NONE;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (opt->opt_fmt[0] == '-' && opt->opt_fmt[1] == '-') {
|
|
Packit |
f00812 |
aux->flags |= IS_LONG;
|
|
Packit |
f00812 |
pname = (const unsigned char *)(opt->opt_fmt + 2);
|
|
Packit |
f00812 |
s->has_long = 1;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
else {
|
|
Packit |
f00812 |
pname = (const unsigned char *)(opt->opt_fmt + 1);
|
|
Packit |
f00812 |
s->has_short = 1;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
aux->printlen = (int) strlen (opt->opt_fmt);
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
aux->namelen = 0;
|
|
Packit |
f00812 |
for (p = pname + 1; *p; p++) {
|
|
Packit |
f00812 |
/* detect required arg */
|
|
Packit |
f00812 |
if (*p == '=' || isspace ((unsigned char)*p)
|
|
Packit |
f00812 |
|| !(aux->flags & IS_LONG)) {
|
|
Packit |
f00812 |
if (aux->namelen == 0)
|
|
Packit |
f00812 |
aux->namelen = p - pname;
|
|
Packit |
f00812 |
aux->flags |= ARG_REQ;
|
|
Packit |
f00812 |
aux->flags &= ~ARG_NONE;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
/* detect optional arg. This overrides required arg. */
|
|
Packit |
f00812 |
if (*p == '[') {
|
|
Packit |
f00812 |
if (aux->namelen == 0)
|
|
Packit |
f00812 |
aux->namelen = p - pname;
|
|
Packit |
f00812 |
aux->flags &= ~(ARG_REQ | ARG_NONE);
|
|
Packit |
f00812 |
aux->flags |= ARG_OPT;
|
|
Packit |
f00812 |
break;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
if (aux->namelen == 0)
|
|
Packit |
f00812 |
aux->namelen = p - pname;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
return (scanopt_t *) s;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
#ifndef NO_SCANOPT_USAGE
|
|
Packit |
f00812 |
/* these structs are for scanopt_usage(). */
|
|
Packit |
f00812 |
struct usg_elem {
|
|
Packit |
f00812 |
int idx;
|
|
Packit |
f00812 |
struct usg_elem *next;
|
|
Packit |
f00812 |
struct usg_elem *alias;
|
|
Packit |
f00812 |
};
|
|
Packit |
f00812 |
typedef struct usg_elem usg_elem;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Prints a usage message based on contents of optlist.
|
|
Packit |
f00812 |
* Parameters:
|
|
Packit |
f00812 |
* scanner - The scanner, already initialized with scanopt_init().
|
|
Packit |
f00812 |
* fp - The file stream to write to.
|
|
Packit |
f00812 |
* usage - Text to be prepended to option list.
|
|
Packit |
f00812 |
* Return: Always returns 0 (zero).
|
|
Packit |
f00812 |
* The output looks something like this:
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
[indent][option, alias1, alias2...][indent][description line1
|
|
Packit |
f00812 |
description line2...]
|
|
Packit |
f00812 |
*/
|
|
Packit |
f00812 |
int scanopt_usage (scanopt_t *scanner, FILE *fp, const char *usage)
|
|
Packit |
f00812 |
{
|
|
Packit |
f00812 |
struct _scanopt_t *s;
|
|
Packit |
f00812 |
int i, columns, indent = 2;
|
|
Packit |
f00812 |
usg_elem *byr_val = NULL; /* option indices sorted by r_val */
|
|
Packit |
f00812 |
usg_elem *store; /* array of preallocated elements. */
|
|
Packit |
f00812 |
int store_idx = 0;
|
|
Packit |
f00812 |
usg_elem *ue;
|
|
Packit |
f00812 |
int maxlen[2];
|
|
Packit |
f00812 |
int desccol = 0;
|
|
Packit |
f00812 |
int print_run = 0;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
maxlen[0] = 0;
|
|
Packit |
f00812 |
maxlen[1] = 0;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
s = (struct _scanopt_t *) scanner;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (usage) {
|
|
Packit |
f00812 |
fprintf (fp, "%s\n", usage);
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
else {
|
|
Packit |
f00812 |
/* Find the basename of argv[0] */
|
|
Packit |
f00812 |
const char *p;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
p = s->argv[0] + strlen (s->argv[0]);
|
|
Packit |
f00812 |
while (p != s->argv[0] && *p != '/')
|
|
Packit |
f00812 |
--p;
|
|
Packit |
f00812 |
if (*p == '/')
|
|
Packit |
f00812 |
p++;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
fprintf (fp, _("Usage: %s [OPTIONS]...\n"), p);
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
fprintf (fp, "\n");
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Sort by r_val and string. Yes, this is O(n*n), but n is small. */
|
|
Packit |
f00812 |
store = malloc((size_t) s->optc * sizeof (usg_elem));
|
|
Packit |
f00812 |
for (i = 0; i < s->optc; i++) {
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* grab the next preallocate node. */
|
|
Packit |
f00812 |
ue = store + store_idx++;
|
|
Packit |
f00812 |
ue->idx = i;
|
|
Packit |
f00812 |
ue->next = ue->alias = NULL;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* insert into list. */
|
|
Packit |
f00812 |
if (!byr_val)
|
|
Packit |
f00812 |
byr_val = ue;
|
|
Packit |
f00812 |
else {
|
|
Packit |
f00812 |
int found_alias = 0;
|
|
Packit |
f00812 |
usg_elem **ue_curr, **ptr_if_no_alias = NULL;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
ue_curr = &byr_val;
|
|
Packit |
f00812 |
while (*ue_curr) {
|
|
Packit |
f00812 |
if (RVAL (s, (*ue_curr)->idx) ==
|
|
Packit |
f00812 |
RVAL (s, ue->idx)) {
|
|
Packit |
f00812 |
/* push onto the alias list. */
|
|
Packit |
f00812 |
ue_curr = &((*ue_curr)->alias);
|
|
Packit |
f00812 |
found_alias = 1;
|
|
Packit |
f00812 |
break;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
if (!ptr_if_no_alias
|
|
Packit |
f00812 |
&&
|
|
Packit |
f00812 |
strcasecmp (NAME (s, (*ue_curr)->idx),
|
|
Packit |
f00812 |
NAME (s, ue->idx)) > 0) {
|
|
Packit |
f00812 |
ptr_if_no_alias = ue_curr;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
ue_curr = &((*ue_curr)->next);
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
if (!found_alias && ptr_if_no_alias)
|
|
Packit |
f00812 |
ue_curr = ptr_if_no_alias;
|
|
Packit |
f00812 |
ue->next = *ue_curr;
|
|
Packit |
f00812 |
*ue_curr = ue;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
#if 0
|
|
Packit |
f00812 |
if (1) {
|
|
Packit |
f00812 |
printf ("ORIGINAL:\n");
|
|
Packit |
f00812 |
for (i = 0; i < s->optc; i++)
|
|
Packit |
f00812 |
printf ("%2d: %s\n", i, NAME (s, i));
|
|
Packit |
f00812 |
printf ("SORTED:\n");
|
|
Packit |
f00812 |
ue = byr_val;
|
|
Packit |
f00812 |
while (ue) {
|
|
Packit |
f00812 |
usg_elem *ue2;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
printf ("%2d: %s\n", ue->idx, NAME (s, ue->idx));
|
|
Packit |
f00812 |
for (ue2 = ue->alias; ue2; ue2 = ue2->next)
|
|
Packit |
f00812 |
printf (" +---> %2d: %s\n", ue2->idx,
|
|
Packit |
f00812 |
NAME (s, ue2->idx));
|
|
Packit |
f00812 |
ue = ue->next;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
#endif
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Now build each row of output. */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* first pass calculate how much room we need. */
|
|
Packit |
f00812 |
for (ue = byr_val; ue; ue = ue->next) {
|
|
Packit |
f00812 |
usg_elem *ap;
|
|
Packit |
f00812 |
int len = 0;
|
|
Packit |
f00812 |
int nshort = 0, nlong = 0;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
#define CALC_LEN(i) do {\
|
|
Packit |
f00812 |
if(FLAGS(s,i) & IS_LONG) \
|
|
Packit |
f00812 |
len += (nlong++||nshort) ? 2+PRINTLEN(s,i) : PRINTLEN(s,i);\
|
|
Packit |
f00812 |
else\
|
|
Packit |
f00812 |
len += (nshort++||nlong)? 2+PRINTLEN(s,i) : PRINTLEN(s,i);\
|
|
Packit |
f00812 |
}while(0)
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (!(FLAGS (s, ue->idx) & IS_LONG))
|
|
Packit |
f00812 |
CALC_LEN (ue->idx);
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* do short aliases first. */
|
|
Packit |
f00812 |
for (ap = ue->alias; ap; ap = ap->next) {
|
|
Packit |
f00812 |
if (FLAGS (s, ap->idx) & IS_LONG)
|
|
Packit |
f00812 |
continue;
|
|
Packit |
f00812 |
CALC_LEN (ap->idx);
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (FLAGS (s, ue->idx) & IS_LONG)
|
|
Packit |
f00812 |
CALC_LEN (ue->idx);
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* repeat the above loop, this time for long aliases. */
|
|
Packit |
f00812 |
for (ap = ue->alias; ap; ap = ap->next) {
|
|
Packit |
f00812 |
if (!(FLAGS (s, ap->idx) & IS_LONG))
|
|
Packit |
f00812 |
continue;
|
|
Packit |
f00812 |
CALC_LEN (ap->idx);
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (len > maxlen[0])
|
|
Packit |
f00812 |
maxlen[0] = len;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* It's much easier to calculate length for description column! */
|
|
Packit |
f00812 |
len = (int) strlen (DESC (s, ue->idx));
|
|
Packit |
f00812 |
if (len > maxlen[1])
|
|
Packit |
f00812 |
maxlen[1] = len;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Determine how much room we have, and how much we will allocate to each col.
|
|
Packit |
f00812 |
* Do not address pathological cases. Output will just be ugly. */
|
|
Packit |
f00812 |
columns = get_cols () - 1;
|
|
Packit |
f00812 |
if (maxlen[0] + maxlen[1] + indent * 2 > columns) {
|
|
Packit |
f00812 |
/* col 0 gets whatever it wants. we'll wrap the desc col. */
|
|
Packit |
f00812 |
maxlen[1] = columns - (maxlen[0] + indent * 2);
|
|
Packit |
f00812 |
if (maxlen[1] < 14) /* 14 is arbitrary lower limit on desc width. */
|
|
Packit |
f00812 |
maxlen[1] = INT_MAX;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
desccol = maxlen[0] + indent * 2;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
#define PRINT_SPACES(fp,n)\
|
|
Packit |
f00812 |
do{\
|
|
Packit |
f00812 |
int _n;\
|
|
Packit |
f00812 |
_n=(n);\
|
|
Packit |
f00812 |
while(_n-- > 0)\
|
|
Packit |
f00812 |
fputc(' ',(fp));\
|
|
Packit |
f00812 |
}while(0)
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Second pass (same as above loop), this time we print. */
|
|
Packit |
f00812 |
/* Sloppy hack: We iterate twice. The first time we print short and long options.
|
|
Packit |
f00812 |
The second time we print those lines that have ONLY long options. */
|
|
Packit |
f00812 |
while (print_run++ < 2) {
|
|
Packit |
f00812 |
for (ue = byr_val; ue; ue = ue->next) {
|
|
Packit |
f00812 |
usg_elem *ap;
|
|
Packit |
f00812 |
int nwords = 0, nchars = 0, has_short = 0;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* TODO: get has_short schtick to work */
|
|
Packit |
f00812 |
has_short = !(FLAGS (s, ue->idx) & IS_LONG);
|
|
Packit |
f00812 |
for (ap = ue->alias; ap; ap = ap->next) {
|
|
Packit |
f00812 |
if (!(FLAGS (s, ap->idx) & IS_LONG)) {
|
|
Packit |
f00812 |
has_short = 1;
|
|
Packit |
f00812 |
break;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
if ((print_run == 1 && !has_short) ||
|
|
Packit |
f00812 |
(print_run == 2 && has_short))
|
|
Packit |
f00812 |
continue;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
PRINT_SPACES (fp, indent);
|
|
Packit |
f00812 |
nchars += indent;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Print, adding a ", " between aliases. */
|
|
Packit |
f00812 |
#define PRINT_IT(i) do{\
|
|
Packit |
f00812 |
if(nwords++)\
|
|
Packit |
f00812 |
nchars+=fprintf(fp,", ");\
|
|
Packit |
f00812 |
nchars+=fprintf(fp,"%s",s->options[i].opt_fmt);\
|
|
Packit |
f00812 |
}while(0)
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (!(FLAGS (s, ue->idx) & IS_LONG))
|
|
Packit |
f00812 |
PRINT_IT (ue->idx);
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* print short aliases first. */
|
|
Packit |
f00812 |
for (ap = ue->alias; ap; ap = ap->next) {
|
|
Packit |
f00812 |
if (!(FLAGS (s, ap->idx) & IS_LONG))
|
|
Packit |
f00812 |
PRINT_IT (ap->idx);
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (FLAGS (s, ue->idx) & IS_LONG)
|
|
Packit |
f00812 |
PRINT_IT (ue->idx);
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* repeat the above loop, this time for long aliases. */
|
|
Packit |
f00812 |
for (ap = ue->alias; ap; ap = ap->next) {
|
|
Packit |
f00812 |
if (FLAGS (s, ap->idx) & IS_LONG)
|
|
Packit |
f00812 |
PRINT_IT (ap->idx);
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* pad to desccol */
|
|
Packit |
f00812 |
PRINT_SPACES (fp, desccol - nchars);
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Print description, wrapped to maxlen[1] columns. */
|
|
Packit |
f00812 |
if (1) {
|
|
Packit |
f00812 |
const char *pstart;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
pstart = DESC (s, ue->idx);
|
|
Packit |
f00812 |
while (1) {
|
|
Packit |
f00812 |
int n = 0;
|
|
Packit |
f00812 |
const char *lastws = NULL, *p;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
p = pstart;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
while (*p && n < maxlen[1]
|
|
Packit |
f00812 |
&& *p != '\n') {
|
|
Packit |
f00812 |
if (isspace ((unsigned char)(*p))
|
|
Packit |
f00812 |
|| *p == '-') lastws =
|
|
Packit |
f00812 |
p;
|
|
Packit |
f00812 |
n++;
|
|
Packit |
f00812 |
p++;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (!*p) { /* hit end of desc. done. */
|
|
Packit |
f00812 |
fprintf (fp, "%s\n",
|
|
Packit |
f00812 |
pstart);
|
|
Packit |
f00812 |
break;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
else if (*p == '\n') { /* print everything up to here then wrap. */
|
|
Packit |
f00812 |
fprintf (fp, "%.*s\n", n,
|
|
Packit |
f00812 |
pstart);
|
|
Packit |
f00812 |
PRINT_SPACES (fp, desccol);
|
|
Packit |
f00812 |
pstart = p + 1;
|
|
Packit |
f00812 |
continue;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
else { /* we hit the edge of the screen. wrap at space if possible. */
|
|
Packit |
f00812 |
if (lastws) {
|
|
Packit |
f00812 |
fprintf (fp,
|
|
Packit |
f00812 |
"%.*s\n",
|
|
Packit |
f00812 |
(int)(lastws - pstart),
|
|
Packit |
f00812 |
pstart);
|
|
Packit |
f00812 |
pstart =
|
|
Packit |
f00812 |
lastws + 1;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
else {
|
|
Packit |
f00812 |
fprintf (fp,
|
|
Packit |
f00812 |
"%.*s\n",
|
|
Packit |
f00812 |
n,
|
|
Packit |
f00812 |
pstart);
|
|
Packit |
f00812 |
pstart = p + 1;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
PRINT_SPACES (fp, desccol);
|
|
Packit |
f00812 |
continue;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
} /* end while */
|
|
Packit |
f00812 |
free (store);
|
|
Packit |
f00812 |
return 0;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
#endif /* no scanopt_usage */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
static int scanopt_err (struct _scanopt_t *s, int is_short, int err)
|
|
Packit |
f00812 |
{
|
|
Packit |
f00812 |
const char *optname = "";
|
|
Packit |
f00812 |
char optchar[2];
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (!s->no_err_msg) {
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (s->index > 0 && s->index < s->argc) {
|
|
Packit |
f00812 |
if (is_short) {
|
|
Packit |
f00812 |
optchar[0] =
|
|
Packit |
f00812 |
s->argv[s->index][s->subscript];
|
|
Packit |
f00812 |
optchar[1] = '\0';
|
|
Packit |
f00812 |
optname = optchar;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
else {
|
|
Packit |
f00812 |
optname = s->argv[s->index];
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
fprintf (stderr, "%s: ", s->argv[0]);
|
|
Packit |
f00812 |
switch (err) {
|
|
Packit |
f00812 |
case SCANOPT_ERR_ARG_NOT_ALLOWED:
|
|
Packit |
f00812 |
fprintf (stderr,
|
|
Packit |
f00812 |
_
|
|
Packit |
f00812 |
("option `%s' doesn't allow an argument\n"),
|
|
Packit |
f00812 |
optname);
|
|
Packit |
f00812 |
break;
|
|
Packit |
f00812 |
case SCANOPT_ERR_ARG_NOT_FOUND:
|
|
Packit |
f00812 |
fprintf (stderr,
|
|
Packit |
f00812 |
_("option `%s' requires an argument\n"),
|
|
Packit |
f00812 |
optname);
|
|
Packit |
f00812 |
break;
|
|
Packit |
f00812 |
case SCANOPT_ERR_OPT_AMBIGUOUS:
|
|
Packit |
f00812 |
fprintf (stderr, _("option `%s' is ambiguous\n"),
|
|
Packit |
f00812 |
optname);
|
|
Packit |
f00812 |
break;
|
|
Packit |
f00812 |
case SCANOPT_ERR_OPT_UNRECOGNIZED:
|
|
Packit |
f00812 |
fprintf (stderr, _("Unrecognized option `%s'\n"),
|
|
Packit |
f00812 |
optname);
|
|
Packit |
f00812 |
break;
|
|
Packit |
f00812 |
default:
|
|
Packit |
f00812 |
fprintf (stderr, _("Unknown error=(%d)\n"), err);
|
|
Packit |
f00812 |
break;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
return err;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Internal. Match str against the regex ^--([^=]+)(=(.*))?
|
|
Packit |
f00812 |
* return 1 if *looks* like a long option.
|
|
Packit |
f00812 |
* 'str' is the only input argument, the rest of the arguments are output only.
|
|
Packit |
f00812 |
* optname will point to str + 2
|
|
Packit |
f00812 |
*
|
|
Packit |
f00812 |
*/
|
|
Packit |
f00812 |
static int matchlongopt (char *str, char **optname, int *optlen, char **arg, int *arglen)
|
|
Packit |
f00812 |
{
|
|
Packit |
f00812 |
char *p;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
*optname = *arg = NULL;
|
|
Packit |
f00812 |
*optlen = *arglen = 0;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Match regex /--./ */
|
|
Packit |
f00812 |
p = str;
|
|
Packit |
f00812 |
if (p[0] != '-' || p[1] != '-' || !p[2])
|
|
Packit |
f00812 |
return 0;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
p += 2;
|
|
Packit |
f00812 |
*optname = p;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* find the end of optname */
|
|
Packit |
f00812 |
while (*p && *p != '=')
|
|
Packit |
f00812 |
++p;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
*optlen = p - *optname;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (!*p)
|
|
Packit |
f00812 |
/* an option with no '=...' part. */
|
|
Packit |
f00812 |
return 1;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* We saw an '=' char. The rest of p is the arg. */
|
|
Packit |
f00812 |
p++;
|
|
Packit |
f00812 |
*arg = p;
|
|
Packit |
f00812 |
while (*p)
|
|
Packit |
f00812 |
++p;
|
|
Packit |
f00812 |
*arglen = p - *arg;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
return 1;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Internal. Look up long or short option by name.
|
|
Packit |
f00812 |
* Long options must match a non-ambiguous prefix, or exact match.
|
|
Packit |
f00812 |
* Short options must be exact.
|
|
Packit |
f00812 |
* Return boolean true if found and no error.
|
|
Packit |
f00812 |
* Error stored in err_code or zero if no error. */
|
|
Packit |
f00812 |
static int find_opt (struct _scanopt_t *s, int lookup_long, char *optstart, int
|
|
Packit |
f00812 |
len, int *err_code, int *opt_offset)
|
|
Packit |
f00812 |
{
|
|
Packit |
f00812 |
int nmatch = 0, lastr_val = 0, i;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
*err_code = 0;
|
|
Packit |
f00812 |
*opt_offset = -1;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (!optstart)
|
|
Packit |
f00812 |
return 0;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
for (i = 0; i < s->optc; i++) {
|
|
Packit |
f00812 |
const char *optname;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
optname = s->options[i].opt_fmt + (lookup_long ? 2 : 1);
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (lookup_long && (s->aux[i].flags & IS_LONG)) {
|
|
Packit |
f00812 |
if (len > s->aux[i].namelen)
|
|
Packit |
f00812 |
continue;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (strncmp (optname, optstart, len) == 0) {
|
|
Packit |
f00812 |
nmatch++;
|
|
Packit |
f00812 |
*opt_offset = i;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* exact match overrides all. */
|
|
Packit |
f00812 |
if (len == s->aux[i].namelen) {
|
|
Packit |
f00812 |
nmatch = 1;
|
|
Packit |
f00812 |
break;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* ambiguity is ok between aliases. */
|
|
Packit |
f00812 |
if (lastr_val
|
|
Packit |
f00812 |
&& lastr_val ==
|
|
Packit |
f00812 |
s->options[i].r_val) nmatch--;
|
|
Packit |
f00812 |
lastr_val = s->options[i].r_val;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
else if (!lookup_long && !(s->aux[i].flags & IS_LONG)) {
|
|
Packit |
f00812 |
if (optname[0] == optstart[0]) {
|
|
Packit |
f00812 |
nmatch++;
|
|
Packit |
f00812 |
*opt_offset = i;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (nmatch == 0) {
|
|
Packit |
f00812 |
*err_code = SCANOPT_ERR_OPT_UNRECOGNIZED;
|
|
Packit |
f00812 |
*opt_offset = -1;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
else if (nmatch > 1) {
|
|
Packit |
f00812 |
*err_code = SCANOPT_ERR_OPT_AMBIGUOUS;
|
|
Packit |
f00812 |
*opt_offset = -1;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
return *err_code ? 0 : 1;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
int scanopt (scanopt_t *svoid, char **arg, int *optindex)
|
|
Packit |
f00812 |
{
|
|
Packit |
f00812 |
char *optname = NULL, *optarg = NULL, *pstart;
|
|
Packit |
f00812 |
int namelen = 0, arglen = 0;
|
|
Packit |
f00812 |
int errcode = 0, has_next;
|
|
Packit |
f00812 |
const optspec_t *optp;
|
|
Packit |
f00812 |
struct _scanopt_t *s;
|
|
Packit |
f00812 |
struct _aux *auxp;
|
|
Packit |
f00812 |
int is_short;
|
|
Packit |
f00812 |
int opt_offset = -1;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
s = (struct _scanopt_t *) svoid;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Normalize return-parameters. */
|
|
Packit |
f00812 |
SAFE_ASSIGN (arg, NULL);
|
|
Packit |
f00812 |
SAFE_ASSIGN (optindex, s->index);
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (s->index >= s->argc)
|
|
Packit |
f00812 |
return 0;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* pstart always points to the start of our current scan. */
|
|
Packit |
f00812 |
pstart = s->argv[s->index] + s->subscript;
|
|
Packit |
f00812 |
if (!pstart)
|
|
Packit |
f00812 |
return 0;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (s->subscript == 0) {
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* test for exact match of "--" */
|
|
Packit |
f00812 |
if (pstart[0] == '-' && pstart[1] == '-' && !pstart[2]) {
|
|
Packit |
f00812 |
SAFE_ASSIGN (optindex, s->index + 1);
|
|
Packit |
f00812 |
INC_INDEX (s, 1);
|
|
Packit |
f00812 |
return 0;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Match an opt. */
|
|
Packit |
f00812 |
if (matchlongopt
|
|
Packit |
f00812 |
(pstart, &optname, &namelen, &optarg, &arglen)) {
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* it LOOKS like an opt, but is it one?! */
|
|
Packit |
f00812 |
if (!find_opt
|
|
Packit |
f00812 |
(s, 1, optname, namelen, &errcode,
|
|
Packit |
f00812 |
&opt_offset)) {
|
|
Packit |
f00812 |
scanopt_err (s, 0, errcode);
|
|
Packit |
f00812 |
return errcode;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
/* We handle this below. */
|
|
Packit |
f00812 |
is_short = 0;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Check for short opt. */
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
else if (pstart[0] == '-' && pstart[1]) {
|
|
Packit |
f00812 |
/* Pass through to below. */
|
|
Packit |
f00812 |
is_short = 1;
|
|
Packit |
f00812 |
s->subscript++;
|
|
Packit |
f00812 |
pstart++;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
else {
|
|
Packit |
f00812 |
/* It's not an option. We're done. */
|
|
Packit |
f00812 |
return 0;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* We have to re-check the subscript status because it
|
|
Packit |
f00812 |
* may have changed above. */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (s->subscript != 0) {
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* we are somewhere in a run of short opts,
|
|
Packit |
f00812 |
* e.g., at the 'z' in `tar -xzf` */
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
optname = pstart;
|
|
Packit |
f00812 |
namelen = 1;
|
|
Packit |
f00812 |
is_short = 1;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (!find_opt
|
|
Packit |
f00812 |
(s, 0, pstart, namelen, &errcode, &opt_offset)) {
|
|
Packit |
f00812 |
return scanopt_err (s, 1, errcode);
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
optarg = pstart + 1;
|
|
Packit |
f00812 |
if (!*optarg) {
|
|
Packit |
f00812 |
optarg = NULL;
|
|
Packit |
f00812 |
arglen = 0;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
else
|
|
Packit |
f00812 |
arglen = (int) strlen (optarg);
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* At this point, we have a long or short option matched at opt_offset into
|
|
Packit |
f00812 |
* the s->options array (and corresponding aux array).
|
|
Packit |
f00812 |
* A trailing argument is in {optarg,arglen}, if any.
|
|
Packit |
f00812 |
*/
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Look ahead in argv[] to see if there is something
|
|
Packit |
f00812 |
* that we can use as an argument (if needed). */
|
|
Packit |
f00812 |
has_next = s->index + 1 < s->argc
|
|
Packit |
f00812 |
&& strcmp ("--", s->argv[s->index + 1]) != 0;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
optp = s->options + opt_offset;
|
|
Packit |
f00812 |
auxp = s->aux + opt_offset;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* case: no args allowed */
|
|
Packit |
f00812 |
if (auxp->flags & ARG_NONE) {
|
|
Packit |
f00812 |
if (optarg && !is_short) {
|
|
Packit |
f00812 |
scanopt_err (s, is_short, errcode = SCANOPT_ERR_ARG_NOT_ALLOWED);
|
|
Packit |
f00812 |
INC_INDEX (s, 1);
|
|
Packit |
f00812 |
return errcode;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
else if (!optarg)
|
|
Packit |
f00812 |
INC_INDEX (s, 1);
|
|
Packit |
f00812 |
else
|
|
Packit |
f00812 |
s->subscript++;
|
|
Packit |
f00812 |
return optp->r_val;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* case: required */
|
|
Packit |
f00812 |
if (auxp->flags & ARG_REQ) {
|
|
Packit |
f00812 |
if (!optarg && !has_next)
|
|
Packit |
f00812 |
return scanopt_err (s, is_short, SCANOPT_ERR_ARG_NOT_FOUND);
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
if (!optarg) {
|
|
Packit |
f00812 |
/* Let the next argv element become the argument. */
|
|
Packit |
f00812 |
SAFE_ASSIGN (arg, s->argv[s->index + 1]);
|
|
Packit |
f00812 |
INC_INDEX (s, 2);
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
else {
|
|
Packit |
f00812 |
SAFE_ASSIGN (arg, (char *) optarg);
|
|
Packit |
f00812 |
INC_INDEX (s, 1);
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
return optp->r_val;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* case: optional */
|
|
Packit |
f00812 |
if (auxp->flags & ARG_OPT) {
|
|
Packit |
f00812 |
SAFE_ASSIGN (arg, optarg);
|
|
Packit |
f00812 |
INC_INDEX (s, 1);
|
|
Packit |
f00812 |
return optp->r_val;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* Should not reach here. */
|
|
Packit |
f00812 |
return 0;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
int scanopt_destroy (scanopt_t *svoid)
|
|
Packit |
f00812 |
{
|
|
Packit |
f00812 |
struct _scanopt_t *s;
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
s = (struct _scanopt_t *) svoid;
|
|
Packit |
f00812 |
if (s != NULL) {
|
|
Packit |
f00812 |
free(s->aux);
|
|
Packit |
f00812 |
free(s);
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
return 0;
|
|
Packit |
f00812 |
}
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
|
|
Packit |
f00812 |
/* vim:set tabstop=8 softtabstop=4 shiftwidth=4: */
|