From acead72c930aa0249c70685114a0e86f1fa55c3f Mon Sep 17 00:00:00 2001 From: Vidar Holen Date: Sun, 29 Oct 2017 17:29:27 -0700 Subject: [PATCH] Improve directive parsing --- ShellCheck/Parser.hs | 66 ++++++++++++++++++++++---------------------- 1 file changed, 33 insertions(+), 33 deletions(-) diff --git a/ShellCheck/Parser.hs b/ShellCheck/Parser.hs index b036bb2..7a3d22c 100644 --- a/ShellCheck/Parser.hs +++ b/ShellCheck/Parser.hs @@ -909,46 +909,46 @@ prop_readAnnotation6 = isOk readAnnotation "# shellcheck disable=SC1234 # shellc readAnnotation = called "shellcheck directive" $ do try readAnnotationPrefix many1 linewhitespace - values <- many1 (readDisable <|> readSourceOverride <|> readShellOverride <|> anyKey) + values <- many1 readKey optional readAnyComment - linefeed + void linefeed <|> do + parseNote ErrorC 1125 "Invalid key=value pair? Ignoring the rest of this directive starting here." + many (noneOf "\n") + void linefeed <|> eof many linewhitespace return $ concat values where - readDisable = forKey "disable" $ - readCode `sepBy` char ',' - where - readCode = do - optional $ string "SC" - int <- many1 digit - return $ DisableComment (read int) - - readSourceOverride = forKey "source" $ do - filename <- many1 $ noneOf " \n" - return [SourceOverride filename] - - readShellOverride = forKey "shell" $ do - pos <- getPosition - shell <- many1 $ noneOf " \n" - when (isNothing $ shellForExecutable shell) $ - parseNoteAt pos ErrorC 1103 - "This shell type is unknown. Use e.g. sh or bash." - return [ShellOverride shell] - - forKey s p = do - try $ string s + readKey = do + keyPos <- getPosition + key <- many1 letter char '=' <|> fail "Expected '=' after directive key" - value <- p - many linewhitespace - return value + annotations <- case key of + "disable" -> readCode `sepBy` char ',' + where + readCode = do + optional $ string "SC" + int <- many1 digit + return $ DisableComment (read int) + + "source" -> do + filename <- many1 $ noneOf " \n" + return [SourceOverride filename] + + "shell" -> do + pos <- getPosition + shell <- many1 $ noneOf " \n" + when (isNothing $ shellForExecutable shell) $ + parseNoteAt pos ErrorC 1103 + "This shell type is unknown. Use e.g. sh or bash." + return [ShellOverride shell] + + _ -> do + parseNoteAt keyPos WarningC 1107 "This directive is unknown. It will be ignored." + anyChar `reluctantlyTill` whitespace + return [] - anyKey = do - pos <- getPosition - noneOf "#\r\n" - anyChar `reluctantlyTill` whitespace many linewhitespace - parseNoteAt pos WarningC 1107 "This directive is unknown. It will be ignored." - return [] + return annotations readAnnotations = do annotations <- many (readAnnotation `thenSkip` allspacing)