/* getopt_long and getopt_long_only entry points for GNU getopt.
   Copyright (C) 1987-1994, 1996-1998, 2004, 2006, 2009-2012 Free Software
   Foundation, Inc.
   This file is part of the GNU C Library.

   This program is free software: you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 3 of the License, or
   (at your option) any later version.

   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */

#ifdef _LIBC
# include <getopt.h>
#else
# include <config.h>
# include "getopt.h"
#endif
#include "getopt_int.h"

#include <stdio.h>

/* This needs to come after some library #include
   to get __GNU_LIBRARY__ defined.  */
#ifdef __GNU_LIBRARY__
#include <stdlib.h>
#endif

#ifndef NULL
#define NULL 0
#endif

int
getopt_long (int argc, char *__getopt_argv_const *argv, const char *options,
             const struct option *long_options, int *opt_index)
{
  return _getopt_internal (argc, (char **) argv, options, long_options,
                           opt_index, 0, 0);
}

int
_getopt_long_r (int argc, char **argv, const char *options,
                const struct option *long_options, int *opt_index,
                struct _getopt_data *d)
{
  return _getopt_internal_r (argc, argv, options, long_options, opt_index,
                             0, d, 0);
}

/* Like getopt_long, but '-' as well as '--' can indicate a long option.
   If an option that starts with '-' (not '--') doesn't match a long option,
   but does match a short option, it is parsed as a short option
   instead.  */

int
getopt_long_only (int argc, char *__getopt_argv_const *argv,
                  const char *options,
                  const struct option *long_options, int *opt_index)
{
  return _getopt_internal (argc, (char **) argv, options, long_options,
                           opt_index, 1, 0);
}

int
_getopt_long_only_r (int argc, char **argv, const char *options,
                     const struct option *long_options, int *opt_index,
                     struct _getopt_data *d)
{
  return _getopt_internal_r (argc, argv, options, long_options, opt_index,
                             1, d, 0);
}


#ifdef TEST

#include <stdio.h>

int
main (int argc, char **argv)
{
  int c;
  int digit_optind = 0;

  while (1)
    {
      int this_option_optind = optind ? optind : 1;
      int option_index = 0;
      static const struct option long_options[] =
      {
        {"add", 1, 0, 0},
        {"append", 0, 0, 0},
        {"delete", 1, 0, 0},
        {"verbose", 0, 0, 0},
        {"create", 0, 0, 0},
        {"file", 1, 0, 0},
        {0, 0, 0, 0}
      };

      c = getopt_long (argc, argv, "abc:d:0123456789",
                       long_options, &option_index);
      if (c == -1)
        break;

      switch (c)
        {
        case 0:
          printf ("option %s", long_options[option_index].name);
          if (optarg)
            printf (" with arg %s", optarg);
          printf ("\n");
          break;

        case '0':
        case '1':
        case '2':
        case '3':
        case '4':
        case '5':
        case '6':
        case '7':
        case '8':
        case '9':
          if (digit_optind != 0 && digit_optind != this_option_optind)
            printf ("digits occur in two different argv-elements.\n");
          digit_optind = this_option_optind;
          printf ("option %c\n", c);
          break;

        case 'a':
          printf ("option a\n");
          break;

        case 'b':
          printf ("option b\n");
          break;

        case 'c':
          printf ("option c with value '%s'\n", optarg);
          break;

        case 'd':
          printf ("option d with value '%s'\n", optarg);
          break;

        case '?':
          break;

        default:
          printf ("?? getopt returned character code 0%o ??\n", c);
        }
    }

  if (optind < argc)
    {
      printf ("non-option ARGV-elements: ");
      while (optind < argc)
        printf ("%s ", argv[optind++]);
      printf ("\n");
    }

  exit (0);
}

#endif /* TEST */
