diff options
author | jilles <jilles@FreeBSD.org> | 2014-05-10 17:42:21 +0000 |
---|---|---|
committer | jilles <jilles@FreeBSD.org> | 2014-05-10 17:42:21 +0000 |
commit | 56ecdb9ab8305061131a36935ec6bbaf949439ba (patch) | |
tree | 3571eb5ebfa9d5f1c5dafb85dcb4962d6f5dc846 | |
parent | 7798d7f7f405786a5591626ffc1c59f60134d434 (diff) | |
download | FreeBSD-src-56ecdb9ab8305061131a36935ec6bbaf949439ba.zip FreeBSD-src-56ecdb9ab8305061131a36935ec6bbaf949439ba.tar.gz |
sh: Don't discard getopts state on unknown option or missing argument.
When getopts finds an invalid option or a missing option-argument, it should
not reset its state and should set OPTIND as normal. This is an old ash bug
that was fixed long ago in dash. Our behaviour now matches most other
shells.
-rw-r--r-- | bin/sh/options.c | 12 | ||||
-rw-r--r-- | bin/sh/tests/builtins/getopts6.0 | 7 | ||||
-rw-r--r-- | bin/sh/tests/builtins/getopts7.0 | 6 |
3 files changed, 17 insertions, 8 deletions
diff --git a/bin/sh/options.c b/bin/sh/options.c index caaa884..8594c57 100644 --- a/bin/sh/options.c +++ b/bin/sh/options.c @@ -480,7 +480,7 @@ atend: INTON; } c = '?'; - goto bad; + goto out; } if (*++q == ':') q++; @@ -501,7 +501,7 @@ atend: INTON; c = '?'; } - goto bad; + goto out; } if (p == **optnext) @@ -511,14 +511,10 @@ atend: } else setvarsafe("OPTARG", "", 0); - ind = *optnext - optfirst + 1; - goto out; -bad: - ind = 1; - *optnext = NULL; - p = NULL; out: + if (*optnext != NULL) + ind = *optnext - optfirst + 1; *optptr = p; fmtstr(s, sizeof(s), "%d", ind); err |= setvarsafe("OPTIND", s, VNOFUNC); diff --git a/bin/sh/tests/builtins/getopts6.0 b/bin/sh/tests/builtins/getopts6.0 new file mode 100644 index 0000000..1d3c39b --- /dev/null +++ b/bin/sh/tests/builtins/getopts6.0 @@ -0,0 +1,7 @@ +# $FreeBSD$ + +set -- -x -y +getopts :x var || echo "First getopts bad: $?" +getopts :x var +r=$? +[ r != 0 ] && [ "$OPTIND" = 3 ] diff --git a/bin/sh/tests/builtins/getopts7.0 b/bin/sh/tests/builtins/getopts7.0 new file mode 100644 index 0000000..3745555 --- /dev/null +++ b/bin/sh/tests/builtins/getopts7.0 @@ -0,0 +1,6 @@ +# $FreeBSD$ + +set -- -x +getopts :x: var +r=$? +[ r != 0 ] && [ "$OPTIND" = 2 ] |