Summary
With --time, du panics with called 'Option::unwrap()' on a 'None' value and aborts (exit 134) when the time-style string is empty. TIME_STYLE=posix- is stripped of its posix- prefix to an empty string and unwraps at du.rs:1236; an empty --time-style= value unwraps at du.rs:1254. In both cases parse_time_style calls .chars().next().unwrap() on an empty string. GNU rejects the empty value with an "ambiguous argument" diagnostic and exits 1 without crashing.
Steps to reproduce
$ mkdir -p /tmp/dudir
$ TIME_STYLE=posix- du --time /tmp/dudir
thread 'main' panicked at src/uu/du/src/du.rs:1236:52:
called `Option::unwrap()` on a `None` value
$ echo $?
134
$ du --time --time-style= /tmp/dudir
thread 'main' panicked at src/uu/du/src/du.rs:1254:41:
called `Option::unwrap()` on a `None` value
$ echo $?
134
Expected behavior
Match GNU: report the error and exit non-zero without crashing.
$ /usr/bin/du --time --time-style= /tmp/dudir
/usr/bin/du: ambiguous argument '' for 'time style'
Valid arguments are:
- 'full-iso'
- 'long-iso'
- 'iso'
- '+FORMAT' (e.g., +%H:%M) for a 'date'-style format
$ echo $?
1
Actual behavior
du panics and aborts with exit code 134. --time is required to reach parse_time_style. Two distinct sites fire depending on where the empty string comes from: the TIME_STYLE environment path strips posix- to empty and unwraps at line 1236; an empty --time-style= argument value reaches the second match and unwraps at line 1254.
Root cause
The environment path strips posix- and unwraps the first char of the (now empty) string:
// src/uu/du/src/du.rs:1235-1236
let s = s.strip_prefix("posix-").unwrap_or(s.as_str());
let s = match s.chars().next().unwrap() {
The argument path unwraps the first char of an empty --time-style= value:
// src/uu/du/src/du.rs:1254
_ => match s.chars().next().unwrap() {
Both .chars().next().unwrap() calls assume a non-empty string. The fix is the same as ls: treat an empty time-style string as the ambiguous-argument error (the DuError::InvalidTimeStyleArg path) instead of unwrapping.
Notes
Found by our static analysis tooling.
Summary
With
--time,dupanics withcalled 'Option::unwrap()' on a 'None' valueand aborts (exit 134) when the time-style string is empty.TIME_STYLE=posix-is stripped of itsposix-prefix to an empty string and unwraps atdu.rs:1236; an empty--time-style=value unwraps atdu.rs:1254. In both casesparse_time_stylecalls.chars().next().unwrap()on an empty string. GNU rejects the empty value with an "ambiguous argument" diagnostic and exits 1 without crashing.Steps to reproduce
Expected behavior
Match GNU: report the error and exit non-zero without crashing.
Actual behavior
dupanics and aborts with exit code 134.--timeis required to reachparse_time_style. Two distinct sites fire depending on where the empty string comes from: theTIME_STYLEenvironment path stripsposix-to empty and unwraps at line 1236; an empty--time-style=argument value reaches the secondmatchand unwraps at line 1254.Root cause
The environment path strips
posix-and unwraps the first char of the (now empty) string:The argument path unwraps the first char of an empty
--time-style=value:Both
.chars().next().unwrap()calls assume a non-empty string. The fix is the same asls: treat an empty time-style string as the ambiguous-argument error (theDuError::InvalidTimeStyleArgpath) instead of unwrapping.Notes
ls(ls panics (unwrap None) on--time-style=posix-(empty after prefix strip) #12629):parse_time_stylecalls.chars().next().unwrap()on a string that is empty after stripping aposix-prefix or an empty--time-style=/TIME_STYLE=.Found by our static analysis tooling.