This blog is under construction

Sunday 3 February 2013

getopt_long example in C


Header file:
    getopt.h

Synopsis:
     int getopt_long (int argc, char *const *argv, const char *shortopts,
               const struct option *longopts, int indexptr);

Description:
     getopt_long can be used to parse long options as well as short options.  It returns -1, if there's no more options to parse.

struct option has four fields.  They are
const char *name   -   represents the name of the option.
int has_arg            -   represents no_argument, required_argument,
                                optional_argument
int *flag  & int val  -   If flag is NULL, getopt_long returns val. Otherwise, flag points
                               to the value in val to indicate that the option was seen.

"--"   -  indicates long option
"-"    -  indicates short opton

longopts[*indexptr].name - represents the name of the long option.
optarg                           - points to the optional argument or required argument.

Please know about getopt to get better understanding on getopt_long


getopt_long function C example


  #include <stdio.h>
  #include <getopt.h>
  #include <string.h>
  #include <stdlib.h>

  struct option longopts[] = {
        {"list",   optional_argument, 0, 'l'},
        {"touch",  required_argument, 0, 'm'},
        {"rm",     required_argument, 0, 'r'},
        {"date",   no_argument,       0, 'd'}
  };

  int main (int argc, char **argv) {
        int i, ch, indexptr = 0;
        char str[100];
        opterr = 0;
        while ((ch = getopt_long(argc, argv, "l::m:r:d",
                                longopts, &indexptr)) != -1) {
                switch (ch) {
                        case 'd':
                                printf("short option - %c  long option - %s\n",
                                        ch, longopts[indexptr].name);
                                system("date");
                                break;
                        case 'l':
                                printf("short option - %c  long option - %s\n",
                                        ch, longopts[indexptr].name);
                                strcpy(str, "ls -l ");
                                if (optarg)
                                        strcat(str, optarg);
                                system(str);
                                break;
                        case 'm':
                                printf("short option - %c  long option - %s\n",
                                        ch, longopts[indexptr].name);
                                strcpy(str, "touch ");
                                strcat(str, optarg);
                                system(str);
                                break;
                        case 'r':
                                printf("short option - %c  long option - %s\n",
                                        ch, longopts[indexptr].name);
                                strcpy(str, "rm ");
                                strcat(str, optarg);
                                system(str);
                                break;

                        case '?':
                                if (optopt == 'r' || optopt == 'm')
                                        printf("Argument is mandatory for --%s\n",
                                                longopts[indexptr].name);
                                else if (isprint (optopt))
                                        printf("U have given an unknown option - %c\n",
                                                        optopt);
                                else
                                        printf("Unknown Error-0x%08x\n", optopt);
                                break;
                        default:
                                exit(0);
                }
        }
        for (i = optind; i < argc; i++)
                printf("Redundant argument - %s\n", argv[i]);
        return 0;
  }



  Output:
  jp@jp-VirtualBox:$ ./a.out --touch file1 --list=file1 --rm file1 --list=file1
  short option - m  long option - touch
  short option - l  long option - list
  -rw-r--r-- 1 jp jp 0 2013-02-03 12:03 file1
  short option - r  long option - rm
  short option - l  long option - list
  ls: cannot access file1: No such file or directory

  jp@jp-VirtualBox:$ ./a.out --date
  short option - d  long option - date
  Sun Feb  3 12:09:58 IST 2013

  jp@jp-VirtualBox:$ ./a.out --rm
  Argument is mandatory for --list

  jp@jp-VirtualBox:$ ./a.out --touch file1 --rm file1 file2 file3
  short option - m  long option - touch
  short option - r  long option - rm
  Redundant argument - file2
  Redundant argument - file3


Notes:
Why optional argument is not parsed by getopt_long or getopt_long_only?
For optional argument, place '=' between option character and its argument.  There should not be any space between option and its argument.

Eg: ./a.out --list=hello
Here, long option "list" will take the optional argument hello since we have '=' between the option and argument.

1 comment:

  1. It has been simply incredibly generous with you to provide openly what exactly many individuals would’ve marketed for an eBook to end up making some cash for their end, primarily given that you could have tried it in the event you wanted.

    Data Science Interview Questions

    Angular JS Interview Questions

    Big Data Training in Velachery

    AWS Certified Developer

    Best Resource of Learning Devops

    Blueprism Interview Questions

    Automation Anywhere Interview Questions

    ReplyDelete