Blame manual/examples/argp-ex3.c

Packit 6c4009
/* Argp example #3 -- a program with options and arguments using argp
Packit 6c4009
   Copyright (C) 1991-2018 Free Software Foundation, Inc.
Packit 6c4009
Packit 6c4009
   This program is free software; you can redistribute it and/or
Packit 6c4009
   modify it under the terms of the GNU General Public License
Packit 6c4009
   as published by the Free Software Foundation; either version 2
Packit 6c4009
   of the License, or (at your option) any later version.
Packit 6c4009
Packit 6c4009
   This program is distributed in the hope that it will be useful,
Packit 6c4009
   but WITHOUT ANY WARRANTY; without even the implied warranty of
Packit 6c4009
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
Packit 6c4009
   GNU General Public License for more details.
Packit 6c4009
Packit 6c4009
   You should have received a copy of the GNU General Public License
Packit 6c4009
   along with this program; if not, if not, see <http://www.gnu.org/licenses/>.
Packit 6c4009
*/
Packit 6c4009
Packit 6c4009
/* This program uses the same features as example 2, and uses options and
Packit 6c4009
   arguments.
Packit 6c4009
Packit 6c4009
   We now use the first four fields in ARGP, so here's a description of them:
Packit 6c4009
     OPTIONS  -- A pointer to a vector of struct argp_option (see below)
Packit 6c4009
     PARSER   -- A function to parse a single option, called by argp
Packit 6c4009
     ARGS_DOC -- A string describing how the non-option arguments should look
Packit 6c4009
     DOC      -- A descriptive string about this program; if it contains a
Packit 6c4009
                 vertical tab character (\v), the part after it will be
Packit 6c4009
                 printed *following* the options
Packit 6c4009
Packit 6c4009
   The function PARSER takes the following arguments:
Packit 6c4009
     KEY  -- An integer specifying which option this is (taken
Packit 6c4009
             from the KEY field in each struct argp_option), or
Packit 6c4009
             a special key specifying something else; the only
Packit 6c4009
             special keys we use here are ARGP_KEY_ARG, meaning
Packit 6c4009
             a non-option argument, and ARGP_KEY_END, meaning
Packit 6c4009
             that all arguments have been parsed
Packit 6c4009
     ARG  -- For an option KEY, the string value of its
Packit 6c4009
             argument, or NULL if it has none
Packit 6c4009
     STATE-- A pointer to a struct argp_state, containing
Packit 6c4009
             various useful information about the parsing state; used here
Packit 6c4009
             are the INPUT field, which reflects the INPUT argument to
Packit 6c4009
             argp_parse, and the ARG_NUM field, which is the number of the
Packit 6c4009
             current non-option argument being parsed
Packit 6c4009
   It should return either 0, meaning success, ARGP_ERR_UNKNOWN, meaning the
Packit 6c4009
   given KEY wasn't recognized, or an errno value indicating some other
Packit 6c4009
   error.
Packit 6c4009
Packit 6c4009
   Note that in this example, main uses a structure to communicate with the
Packit 6c4009
   parse_opt function, a pointer to which it passes in the INPUT argument to
Packit 6c4009
   argp_parse.  Of course, it's also possible to use global variables
Packit 6c4009
   instead, but this is somewhat more flexible.
Packit 6c4009
Packit 6c4009
   The OPTIONS field contains a pointer to a vector of struct argp_option's;
Packit 6c4009
   that structure has the following fields (if you assign your option
Packit 6c4009
   structures using array initialization like this example, unspecified
Packit 6c4009
   fields will be defaulted to 0, and need not be specified):
Packit 6c4009
     NAME   -- The name of this option's long option (may be zero)
Packit 6c4009
     KEY    -- The KEY to pass to the PARSER function when parsing this option,
Packit 6c4009
               *and* the name of this option's short option, if it is a
Packit 6c4009
               printable ascii character
Packit 6c4009
     ARG    -- The name of this option's argument, if any
Packit 6c4009
     FLAGS  -- Flags describing this option; some of them are:
Packit 6c4009
                 OPTION_ARG_OPTIONAL -- The argument to this option is optional
Packit 6c4009
                 OPTION_ALIAS        -- This option is an alias for the
Packit 6c4009
                                        previous option
Packit 6c4009
                 OPTION_HIDDEN       -- Don't show this option in --help output
Packit 6c4009
     DOC    -- A documentation string for this option, shown in --help output
Packit 6c4009
Packit 6c4009
   An options vector should be terminated by an option with all fields zero. */
Packit 6c4009
Packit 6c4009
#include <stdlib.h>
Packit 6c4009
#include <argp.h>
Packit 6c4009
Packit 6c4009
const char *argp_program_version =
Packit 6c4009
  "argp-ex3 1.0";
Packit 6c4009
const char *argp_program_bug_address =
Packit 6c4009
  "<bug-gnu-utils@@gnu.org>";
Packit 6c4009
Packit 6c4009
/* Program documentation.  */
Packit 6c4009
static char doc[] =
Packit 6c4009
  "Argp example #3 -- a program with options and arguments using argp";
Packit 6c4009
Packit 6c4009
/* A description of the arguments we accept.  */
Packit 6c4009
static char args_doc[] = "ARG1 ARG2";
Packit 6c4009
Packit 6c4009
/* The options we understand.  */
Packit 6c4009
static struct argp_option options[] = {
Packit 6c4009
  {"verbose",  'v', 0,      0,  "Produce verbose output" },
Packit 6c4009
  {"quiet",    'q', 0,      0,  "Don't produce any output" },
Packit 6c4009
  {"silent",   's', 0,      OPTION_ALIAS },
Packit 6c4009
  {"output",   'o', "FILE", 0,
Packit 6c4009
   "Output to FILE instead of standard output" },
Packit 6c4009
  { 0 }
Packit 6c4009
};
Packit 6c4009
Packit 6c4009
/* Used by @code{main} to communicate with @code{parse_opt}.  */
Packit 6c4009
struct arguments
Packit 6c4009
{
Packit 6c4009
  char *args[2];		/* @var{arg1} & @var{arg2} */
Packit 6c4009
  int silent, verbose;
Packit 6c4009
  char *output_file;
Packit 6c4009
};
Packit 6c4009
Packit 6c4009
/* Parse a single option.  */
Packit 6c4009
static error_t
Packit 6c4009
parse_opt (int key, char *arg, struct argp_state *state)
Packit 6c4009
{
Packit 6c4009
  /* Get the @var{input} argument from @code{argp_parse}, which we
Packit 6c4009
     know is a pointer to our arguments structure.  */
Packit 6c4009
  struct arguments *arguments = state->input;
Packit 6c4009
Packit 6c4009
  switch (key)
Packit 6c4009
    {
Packit 6c4009
    case 'q': case 's':
Packit 6c4009
      arguments->silent = 1;
Packit 6c4009
      break;
Packit 6c4009
    case 'v':
Packit 6c4009
      arguments->verbose = 1;
Packit 6c4009
      break;
Packit 6c4009
    case 'o':
Packit 6c4009
      arguments->output_file = arg;
Packit 6c4009
      break;
Packit 6c4009
Packit 6c4009
    case ARGP_KEY_ARG:
Packit 6c4009
      if (state->arg_num >= 2)
Packit 6c4009
	/* Too many arguments.  */
Packit 6c4009
	argp_usage (state);
Packit 6c4009
Packit 6c4009
      arguments->args[state->arg_num] = arg;
Packit 6c4009
Packit 6c4009
      break;
Packit 6c4009
Packit 6c4009
    case ARGP_KEY_END:
Packit 6c4009
      if (state->arg_num < 2)
Packit 6c4009
	/* Not enough arguments.  */
Packit 6c4009
	argp_usage (state);
Packit 6c4009
      break;
Packit 6c4009
Packit 6c4009
    default:
Packit 6c4009
      return ARGP_ERR_UNKNOWN;
Packit 6c4009
    }
Packit 6c4009
  return 0;
Packit 6c4009
}
Packit 6c4009
Packit 6c4009
/* Our argp parser.  */
Packit 6c4009
static struct argp argp = { options, parse_opt, args_doc, doc };
Packit 6c4009
Packit 6c4009
int
Packit 6c4009
main (int argc, char **argv)
Packit 6c4009
{
Packit 6c4009
  struct arguments arguments;
Packit 6c4009
Packit 6c4009
  /* Default values.  */
Packit 6c4009
  arguments.silent = 0;
Packit 6c4009
  arguments.verbose = 0;
Packit 6c4009
  arguments.output_file = "-";
Packit 6c4009
Packit 6c4009
  /* Parse our arguments; every option seen by @code{parse_opt} will
Packit 6c4009
     be reflected in @code{arguments}.  */
Packit 6c4009
  argp_parse (&argp, argc, argv, 0, 0, &arguments);
Packit 6c4009
Packit 6c4009
  printf ("ARG1 = %s\nARG2 = %s\nOUTPUT_FILE = %s\n"
Packit 6c4009
	  "VERBOSE = %s\nSILENT = %s\n",
Packit 6c4009
	  arguments.args[0], arguments.args[1],
Packit 6c4009
	  arguments.output_file,
Packit 6c4009
	  arguments.verbose ? "yes" : "no",
Packit 6c4009
	  arguments.silent ? "yes" : "no");
Packit 6c4009
Packit 6c4009
  exit (0);
Packit 6c4009
}