Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is it possible to repeat getopt

Tags:

c

getopt

I'm trying to create a basic shell with builtin commands, and I'm having some issues with getopt. Here is the output (using valgrind):

$ mkdir -p foo/bar
mkdir
-p
foo/bar
FLAGON
$ mkdir -p foo/test
mkdir
-p
foo/test
==15377== Invalid read of size 1
==15377==    at 0x5201BBE: _getopt_internal_r (in /usr/lib/libc-2.17.so)
==15377==    by 0x5202CEA: _getopt_internal (in /usr/lib/libc-2.17.so)
==15377==    by 0x5202D37: getopt (in /usr/lib/libc-2.17.so)
==15377==    by 0x40351A: shell_ns_cmd_mkdir (shell.c:542)
==15377==    by 0x403AB4: normal_shell_cb (shell.c:610)
==15377==    by 0x402E8E: shell_mainloop (shell.c:402)
==15377==    by 0x401B67: main (main.c:52)
==15377==  Address 0x54e0912 is 2 bytes inside a block of size 3 free'd
==15377==    at 0x4C2AD3C: free (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==15377==    by 0x402C93: shell_mainloop (shell.c:384)
==15377==    by 0x401B67: main (main.c:52)
==15377== 
$ 

And here is the source (clipped):

for (i = 0; i < argc; i++) {
    puts(argv[i]);
}
while ((c = getopt(argc, argv, "p")) != -1) {
    switch (c) {
        case 'p':
            puts("FLAGON");
            mkparents = true;
            break;
        case '?':
            fprintf(stderr, "invalid option -- %c", optopt);
            ret = 127;
            goto end;
            break;
    }
}

So the first time it runs it (mkdir -p) recognizes it (-p) and the second time it runs, it doesn't. Any ideas?

like image 821
MiJyn Avatar asked Mar 02 '13 22:03

MiJyn


People also ask

What does getopt return?

RETURN VALUE The getopt() function returns the next option character specified on the command line. A colon (:) is returned if getopt() detects a missing argument and the first character of optstring was a colon (:).

What is getopt used for?

The getopt() function is a builtin function in C and is used to parse command line arguments. Syntax: getopt(int argc, char *const argv[], const char *optstring) optstring is simply a list of characters, each representing a single character option.

What is Optarg getopt?

optarg indicates an optional parameter to a command line option. opterr can be set to 0 to prevent getopt() from printing error messages. optind is the index of the next element of the argument list to be process, and optopt is the command line option last matched.

What is Optstring in getopt?

According to getopt manual: "The argument optstring is a string of recognized option characters; if a character is followed by a colon, the option takes an argument."


1 Answers

If you want to scan multiple vectors you need to reset getopt by setting optind to 1.

The variable optind is the index of the next element of the argv[] vector to be processed. It shall be initialized to 1 by the system, and getopt() shall update it when it finishes with each element of argv[].

If setting optind to 1 doesn't work, also try 0, I think I remember reading about that somewhere.

like image 122
cnicutar Avatar answered Oct 13 '22 21:10

cnicutar