diff --git a/ShellCheck/Analytics.hs b/ShellCheck/Analytics.hs index 2b28bf4703ab9a922ff7e4192632c72536aff45c..6f92155f3369cf5904311e788388276a0b0ad124 100644 --- a/ShellCheck/Analytics.hs +++ b/ShellCheck/Analytics.hs @@ -73,11 +73,13 @@ checksFor Sh = [ checkBashisms ,checkTimeParameters ,checkForDecimals + ,checkTimedCommand ] checksFor Dash = [ checkBashisms ,checkForDecimals ,checkLocalScope + ,checkTimedCommand ] checksFor Ksh = [ checkEchoSed @@ -1107,8 +1109,8 @@ checkStderrRedirect params redir@(T_Redirecting _ [ checkStderrRedirect _ _ = return () -lt x = trace ("FAILURE " ++ show x) x -ltt t = trace ("FAILURE " ++ show t) +lt x = trace ("Tracing " ++ show x) x +ltt t = trace ("Tracing " ++ show t) prop_checkSingleQuotedVariables = verify checkSingleQuotedVariables "echo '$foo'" @@ -1863,6 +1865,32 @@ checkTimeParameters _ = checkUnqualifiedCommand "time" f where info (getId cmd) 2023 "The shell may override 'time' as seen in man time(1). Use 'command time ..' for that one." f _ _ = return () +prop_checkTimedCommand1 = verify checkTimedCommand "time -p foo | bar" +prop_checkTimedCommand2 = verify checkTimedCommand "time ( foo; bar; )" +prop_checkTimedCommand3 = verifyNot checkTimedCommand "time sleep 1" +checkTimedCommand _ = checkUnqualifiedCommand "time" f where + f c args@(_:_) = do + let cmd = last args + when (isPiped cmd) $ + warn (getId c) 2176 "'time' is undefined for pipelines. time single stage or sh -c instead." + when (isSimple cmd == Just False) $ + warn (getId cmd) 2177 "'time' is undefined for compound commands, time sh -c instead." + f _ _ = return () + isPiped cmd = + case cmd of + T_Pipeline _ _ (_:_:_) -> True + _ -> False + getCommand cmd = + case cmd of + T_Pipeline _ _ ((T_Redirecting _ _ a):_) -> return a + _ -> fail "" + isSimple cmd = do + innerCommand <- getCommand cmd + case innerCommand of + T_SimpleCommand {} -> return True + _ -> return False + + prop_checkTestRedirects1 = verify checkTestRedirects "test 3 > 1" prop_checkTestRedirects2 = verifyNot checkTestRedirects "test 3 \\> 1" prop_checkTestRedirects3 = verify checkTestRedirects "/usr/bin/test $var > $foo" diff --git a/quicktest b/quicktest index f4af17597d10d74443d2c5663558754f65bfc2d4..877ad6c1fb7d43f46db7fc1e106b5dfc9ea04d27 100755 --- a/quicktest +++ b/quicktest @@ -4,12 +4,12 @@ # 'cabal test' remains the source of truth. ( - var=$(echo 'liftM and $ sequence [ShellCheck.Analytics.runTests, ShellCheck.Parser.runTests, ShellCheck.Checker.runTests]' | cabal repl | tee /dev/stderr) + var=$(echo 'liftM and $ sequence [ShellCheck.Analytics.runTests, ShellCheck.Parser.runTests, ShellCheck.Checker.runTests]' | cabal repl 2>&1 | tee /dev/stderr) if [[ $var == *$'\nTrue'* ]] then exit 0 else - grep -C 3 "Fail" <<< "$var" + grep -C 3 -e "Fail" -e "Tracing" <<< "$var" exit 1 fi ) 2>&1