diff --git a/src/cmd/ksh93/sh/xec.c b/src/cmd/ksh93/sh/xec.c index c691486c2..87089bec2 100644 --- a/src/cmd/ksh93/sh/xec.c +++ b/src/cmd/ksh93/sh/xec.c @@ -295,9 +295,6 @@ static void p_time(Shell_t *shp, Sfio_t *out, const char *format, clock_t *tm) continue; unsigned char l_modifier = 0; int precision = 3; -#ifndef timeofday - n = 0; -#endif sfwrite(stkp, first, format-first); c = *++format; @@ -353,8 +350,9 @@ static void p_time(Shell_t *shp, Sfio_t *out, const char *format, clock_t *tm) tvp = &tm[TM_SYS_IDX]; else { + stkseek(stkp,offset); errormsg(SH_DICT,ERROR_exit(0),e_badtformat,c); - continue; + return; } if(l_modifier) l_time(stkp, tvp, precision); @@ -362,15 +360,21 @@ static void p_time(Shell_t *shp, Sfio_t *out, const char *format, clock_t *tm) { /* scale fraction from micro to milli, centi, or deci second according to precision */ int n, frac = tvp->tv_usec; - for(n = 3 + (3 - precision); n > 0; --n) frac /= 10; - sfprintf(stkp, "%d%c%0*d", tvp->tv_sec, GETDECIMAL(0), precision, frac); + for(n = 3 + (3 - precision); n > 0; --n) + frac /= 10; + if(precision) + sfprintf(stkp, "%d%c%0*d", tvp->tv_sec, GETDECIMAL(0), precision, frac); + else + sfprintf(stkp, "%d", tvp->tv_sec); } #else - if(c=='U') + if(c=='R') + n = 0; + else if(c=='U') n = 1; else if(c=='S') n = 2; - else if(c!='R') + else { stkseek(stkp,offset); errormsg(SH_DICT,ERROR_exit(0),e_badtformat,c); diff --git a/src/cmd/ksh93/tests/basic.sh b/src/cmd/ksh93/tests/basic.sh index 2594569d5..4ba3d4bd7 100755 --- a/src/cmd/ksh93/tests/basic.sh +++ b/src/cmd/ksh93/tests/basic.sh @@ -553,25 +553,31 @@ $SHELL 2> /dev/null -c $'for i;\ndo :;done' || err_exit 'for i ; not v ) || err_exit "crash when sourcing multiple files (exit status $?)" # ====== -# The time keyword should correctly handle millisecond precision. -# This can be checked by verifying the last digit is not a zero -# when 'time sleep .002' is run. +# The time keyword should correctly handle millisecond precision, except +# on older systems that do not support getrusage(2) or gettimeofday(2). result=$( TIMEFORMAT=$'\%3R' redirect 2>&1 time sleep .002 ) -[[ ${result: -1} == 0 ]] && err_exit "the 'time' keyword doesn't properly support millisecond precision" +case $result in +0.000 | 0.010) + err_exit "warning: 'time' keyword doesn't support millisecond precision" + let "Errors--" ;; +0.002) ;; +*) err_exit "'time' keyword, millisecond precision: expected 0.002, got $result" ;; +esac # A single '%' after a format specifier should not be a syntax # error (it should be treated as a literal '%'). -IFS=' ' -result=( $( +expect='0%' +actual=$( TIMEFORMAT=$'%0S%' redirect 2>&1 time : -) ) -[[ ${result[4]} == bad ]] && err_exit "'%' is not treated literally when placed after a format specifier" +) +[[ $actual == "$expect" ]] || err_exit "'%' is not treated literally when placed after a format specifier" \ + "(expected $(printf %q "$expect"), got $(printf %q "$actual"))" # The locale's radix point shouldn't be ignored us=$(