From: Marcin Siodelski Date: Thu, 21 Jun 2012 12:42:13 +0000 (+0200) Subject: [master] Workaround for getopt() bug in glibc. X-Git-Tag: trac2351_base~223 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=141b8cb757874ff34e7ae70cab01ee6b0c8f3f60;p=thirdparty%2Fkea.git [master] Workaround for getopt() bug in glibc. --- diff --git a/tests/tools/perfdhcp/command_options.cc b/tests/tools/perfdhcp/command_options.cc index 5b4f4249fb..09393bbc3d 100644 --- a/tests/tools/perfdhcp/command_options.cc +++ b/tests/tools/perfdhcp/command_options.cc @@ -88,7 +88,25 @@ CommandOptions::parse(int argc, char** const argv) { // Reset internal variables used by getopt // to eliminate undefined behavior when // parsing different command lines multiple times + +#ifdef __GLIBC__ + // Warning: non-portable code. This is due to a bug in glibc's + // getopt() which keeps internal state about an old argument vector + // (argc, argv) from last call and tries to scan them when a new + // argument vector (argc, argv) is passed. As the old vector may not + // be main()'s arguments, but heap allocated and may have been freed + // since, this becomes a use after free and results in random + // behavior. According to the NOTES section in glibc getopt()'s + // manpage, setting optind=0 resets getopt()'s state. Though this is + // not required in our usage of getopt(), the bug still happens + // unless we set optind=0. + // + // Setting optind=0 is non-portable code. + optind = 0; +#else optind = 1; +#endif + opterr = 0; // Reset values of class members