On Sun, May 19, 2024 at 10:21:42PM +0800, Herbert Xu wrote: > Always reset OPTIND if it is modified by the user, regardless of > its value. I disagree in principle, but I think this is basically fine actually; strictly, we are allowed to do this 98842 If the application sets OPTIND to the value 1, a new set of parameters can be used: either the 98843 current positional parameters or new arg values. Any other attempt to invoke getopts multiple 98844 times in a single shell execution environment with parameters (positional parameters or arg 98845 operands) that are not the same in all invocations, or with an OPTIND value modified to be a 98846 value other than 1, produces unspecified results. but I cannot prove this breaks existing code in the wild. I mean such code most likely definitely exists, but I cannot prove this; but even if it does, it relies on "unspecified" behaviour, which means it "cannot be assured to be portable across conforming implementations" such as dash 1 and dash 2. I still think it should keep working, since it had worked. While I found at least one changelog entry in DCS saying "remove unset OPTIND to work around broken dash shell" by searching for "unset.*OPTIND\b", searching "OPTIND=[^01]" gives me heaps of OPTIND=digit and OPTIND=expression users, but most of them are explicit bash users; the first one with /bin/sh is https://sources.debian.org/src/sptk/3.9-3/debian/scripts/raw2wav/?hl=74#L74 reading OPTIND=0 OPT="" for i in "$@" do OPTIND=`expr $OPTIND + 1` if [ "$OPT" = "" ] then OPTARG="" but this program doesn't use getopts. This turns "unset OPTIND must work but doesn't" + "OPTIND=asd is invalid but probably shouldn't be" + "OPTIND=3 makes getopts parse the third argument (as a happy accident)" into "unset OPTIND works" + "OPTIND=asd works (and restarts getopts as a happy accident)" + "OPTIND=3 restarts getopts (as a happy accident)". So, overall, reasonable, if a tad solomonic.
Attachment:
signature.asc
Description: PGP signature