I have an old saved tab with the MUSL configure script. A few things struck me on first glance- like the fact it is written using sh rather than bash, and it has a noticeably terse style. But I had to take a closer look at the argument parsing logic!
The For Loop #
https://github.com/bminor/musl/blob/master/configure#L147
1for arg; do
2 ...
3done
How is arg being set?
This is a terse form of a for loop in shell. It can also be written more verbosely to a familiar form:
1for arg in "$@"; do
2 ...
3done
So, arg is set to each argument supplied to the script.
Argument Parsing #
https://github.com/bminor/musl/blob/master/configure#L14A8
1case "$arg" in
2 --help|-h) usage ;;
3 --srcdir=*) srcdir=${arg#*=} ;;
4 --prefix=*) prefix=${arg#*=} ;;
5 ...
6 --enable-shared|--enable-shared=yes) shared=yes ;;
7 ...
8 *) build=$arg ; target=$arg ;;
9esac
What is srcdir or prefix being set to?
If arg is --srcdir=/some/path, the variable srcdir is set to '/some/path`.
How does ${arg#*=}
work?
This is a variety of parameter expansion that is in POSIX shell (not just bash). The specification says:
${parameter#[word]}
Remove Smallest Prefix Pattern. The word shall be expanded to produce a pattern. The parameter expansion shall then result in parameter, with the smallest portion of the prefix matched by the pattern deleted. If present, word shall not begin with an unquoted '#'.
In the case above, word is '*='. As a shell pattern matching expression, that means zero or more characters ('*') followed by an equals sign.
1$ ( arg='undergrad'; v=${arg#*g}; echo "$v" ) # delete everything through the first "g"
2rad
3$ ( arg='foo:bar'; v=${arg#*:}; echo "$v" ) # delete everything through the first ":"
4bar
References #
- POSIX.1-2017 Shell Command Language: for loops
- POSIX.1-2017 Shell Command Language: Parameter Expansion
- pure sh bible: Prefix and Suffix Deletion