From 307bc3edceecdb18fb22250c95a0ec1c29e93da9 Mon Sep 17 00:00:00 2001 From: Johnothan King Date: Thu, 13 Jan 2022 04:17:36 -0800 Subject: [PATCH] time: Fix precision bug in times(3) fallback (#425) In the times(3) fallback for the time keyword (which can be enabled in xec.c by undefining _lib_getrusage and timeofday), ksh will print the obtained time incorrectly if TIMEFORMAT is set to use a precision level of three: $ TIMEFORMAT=$'\nreal\t%3lR' $ time sleep .080 real 0m00.008s # Should be '00.080s' This commit corrects that issue by using 10^precision to get the correct fractional scaling. Note that the fallback still doesn't support a true precision level of three (times(3) alone doesn't support it), so this in effect pads a zero to the end of the output when the precision level is three. Additional change to tests/builtins.sh: - While fixing the above issue I found out that ksh93v- broke support for passing microseconds to the sleep builtin in the form of U. I've added a regression test for that bug to ensure it isn't backported to ksh93u+m by accident. Co-authored-by: Martijn Dekker --- src/cmd/ksh93/sh/xec.c | 2 +- src/cmd/ksh93/tests/builtins.sh | 5 +++++ 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/src/cmd/ksh93/sh/xec.c b/src/cmd/ksh93/sh/xec.c index 5c673e828..c466f01b1 100644 --- a/src/cmd/ksh93/sh/xec.c +++ b/src/cmd/ksh93/sh/xec.c @@ -225,7 +225,7 @@ static void l_time(Sfio_t *outfile,register clock_t t,int precision) if(precision) { frac = t%sh.lim.clk_tck; - frac = (frac*100)/sh.lim.clk_tck; + frac = (frac*(int)pow(10,precision))/sh.lim.clk_tck; } t /= sh.lim.clk_tck; sec = t%60; diff --git a/src/cmd/ksh93/tests/builtins.sh b/src/cmd/ksh93/tests/builtins.sh index a2e0d92bf..8b61aef74 100755 --- a/src/cmd/ksh93/tests/builtins.sh +++ b/src/cmd/ksh93/tests/builtins.sh @@ -1516,5 +1516,10 @@ if builtin tail 2> /dev/null; then "(expected $(printf %q "$exp"), got $(printf %q "$got"))" fi +# ====== +# ksh93v- accidentally broke the sleep builtin's support for +# using microseconds in the form of U. +got=$(sleep 1U 2>&1) || err_exit "sleep builtin cannot handle microseconds in the form of U (got $(printf %q "$got"))" + # ====== exit $((Errors<125?Errors:125))