Skip to content

Commit

Permalink
Restrict type of parens and brackets to prevent negative use of NExprLoc
Browse files Browse the repository at this point in the history
it is not generally appropriate to have higher-order parsers operate on
annotated locations as they are liable to perform changes to the parser which
are not captured in the annotation.

See #739 and
#744 for examples.
  • Loading branch information
expipiplus1 committed Oct 29, 2020
1 parent cbe995c commit b00c6fa
Showing 1 changed file with 9 additions and 2 deletions.
11 changes: 9 additions & 2 deletions src/Nix/Parser.hs
Original file line number Diff line number Diff line change
Expand Up @@ -200,7 +200,7 @@ nixNull = annotateLocation1 (mkNullF <$ reserved "null" <?> "null")
-- however this position doesn't include the parsed parentheses, so remove the
-- "inner" location annotateion and annotate again, including the parentheses.
nixParens :: Parser NExprLoc
nixParens = annotateLocation1 (stripAnn . unFix <$> (parens nixToplevelForm <?> "parens"))
nixParens = annotateLocation1 (parens (stripAnn . unFix <$> nixToplevelForm) <?> "parens")

nixList :: Parser NExprLoc
nixList = annotateLocation1 (brackets (NList <$> many nixTerm) <?> "list")
Expand Down Expand Up @@ -411,7 +411,7 @@ nixBinders = (inherit <+> namedVar) `endBy` semi where
<*> (equals *> nixToplevelForm)
<*> pure p
<?> "variable binding"
scope = parens nixToplevelForm <?> "inherit scope"
scope = nixParens <?> "inherit scope"

keyName :: Parser (NKeyName NExprLoc)
keyName = dynamicKey <+> staticKey where
Expand Down Expand Up @@ -496,6 +496,13 @@ identifier = lexeme $ try $ do
where
identLetter x = isAlpha x || isDigit x || x == '_' || x == '\'' || x == '-'

-- We restrict the type of 'parens' and 'brackets' here because if they were to
-- take a @Parser NExprLoc@ argument they would parse additional text which
-- wouldn't be captured in the source location annotation.
--
-- Braces and angles in hnix don't enclose a single expression so this type
-- restriction would not be useful.
parens, brackets :: Parser (NExprF f) -> Parser (NExprF f)
parens = between (symbol "(") (symbol ")")
braces = between (symbol "{") (symbol "}")
-- angles = between (symbol "<") (symbol ">")
Expand Down

0 comments on commit b00c6fa

Please sign in to comment.