diff options
author | Péter Diviánszky <divipp@gmail.com> | 2016-02-23 23:28:13 +0100 |
---|---|---|
committer | Péter Diviánszky <divipp@gmail.com> | 2016-02-23 23:28:13 +0100 |
commit | 44ce14d48b02c5c3f9f54db53e7dbc6f1fd49038 (patch) | |
tree | 8cfadfaebb2a5dd7b96ee4363e92a9b3e7112920 /src/LambdaCube | |
parent | cad46122ad471492eb42f6464cb33fc537f95d67 (diff) |
simplify namespace handling
Diffstat (limited to 'src/LambdaCube')
-rw-r--r-- | src/LambdaCube/Compiler/Lexer.hs | 34 | ||||
-rw-r--r-- | src/LambdaCube/Compiler/Parser.hs | 36 |
2 files changed, 25 insertions, 45 deletions
diff --git a/src/LambdaCube/Compiler/Lexer.hs b/src/LambdaCube/Compiler/Lexer.hs index f7c96bf6..a8de998b 100644 --- a/src/LambdaCube/Compiler/Lexer.hs +++ b/src/LambdaCube/Compiler/Lexer.hs | |||
@@ -196,50 +196,36 @@ psn p = appRange $ flip (,) <$> p | |||
196 | 196 | ||
197 | -------------------------------------------------------------------------------- namespace handling | 197 | -------------------------------------------------------------------------------- namespace handling |
198 | 198 | ||
199 | data Level = TypeLevel | ExpLevel | 199 | data Namespace = TypeNS | ExpNS |
200 | deriving (Eq, Show) | 200 | deriving (Eq, Show) |
201 | 201 | ||
202 | data Namespace = Namespace | 202 | tick = (\case TypeNS -> switchTick; _ -> id) |
203 | { namespaceLevel :: Maybe Level | ||
204 | , constructorNamespace :: Bool -- True means that the case of the first letter of identifiers matters | ||
205 | } | ||
206 | deriving (Show) | ||
207 | |||
208 | namespace' = namespaceLevel <$> namespace | ||
209 | |||
210 | tick = (\case TypeLevel -> switchTick; _ -> id) . fromMaybe ExpLevel . namespaceLevel | ||
211 | 203 | ||
212 | tick' c = (`tick` c) <$> namespace | 204 | tick' c = (`tick` c) <$> namespace |
213 | 205 | ||
214 | switchNamespace = \case ExpLevel -> TypeLevel; TypeLevel -> ExpLevel | 206 | switchNamespace = \case ExpNS -> TypeNS; TypeNS -> ExpNS |
215 | 207 | ||
216 | switchTick ('\'': n) = n | 208 | switchTick ('\'': n) = n |
217 | switchTick n = '\'': n | 209 | switchTick n = '\'': n |
218 | 210 | ||
219 | modifyLevel f = local $ (first . second) $ \(Namespace l p) -> Namespace (f <$> l) p | 211 | modifyLevel f = local $ first $ second f |
220 | 212 | ||
221 | typeNS, expNS, switchNS :: P a -> P a | 213 | typeNS, expNS, switchNS :: P a -> P a |
222 | typeNS = modifyLevel $ const TypeLevel | 214 | typeNS = modifyLevel $ const TypeNS |
223 | expNS = modifyLevel $ const ExpLevel | 215 | expNS = modifyLevel $ const ExpNS |
224 | switchNS = modifyLevel $ switchNamespace | 216 | switchNS = modifyLevel $ switchNamespace |
225 | 217 | ||
226 | ifNoCNamespace p = namespace >>= \ns -> if constructorNamespace ns then mzero else p | ||
227 | |||
228 | -------------------------------------------------------------------------------- identifiers | 218 | -------------------------------------------------------------------------------- identifiers |
229 | 219 | ||
230 | lcIdentStart = satisfy $ \c -> isLower c || c == '_' | 220 | lowerLetter = satisfy $ \c -> isLower c || c == '_' |
221 | upperLetter = satisfy isUpper | ||
231 | identStart = satisfy $ \c -> isLetter c || c == '_' | 222 | identStart = satisfy $ \c -> isLetter c || c == '_' |
232 | identLetter = satisfy $ \c -> isAlphaNum c || c == '_' || c == '\'' || c == '#' | 223 | identLetter = satisfy $ \c -> isAlphaNum c || c == '_' || c == '\'' || c == '#' |
233 | lowercaseOpLetter = oneOf "!#$%&*+./<=>?@\\^|-~" | 224 | lowercaseOpLetter = oneOf "!#$%&*+./<=>?@\\^|-~" |
234 | opLetter = oneOf ":!#$%&*+./<=>?@\\^|-~" | 225 | opLetter = lowercaseOpLetter <|> char ':' |
235 | 226 | ||
236 | maybeStartWith p i = i <|> (:) <$> satisfy p <*> i | 227 | maybeStartWith p i = i <|> (:) <$> satisfy p <*> i |
237 | 228 | ||
238 | lowerLetter = lcIdentStart <|> ifNoCNamespace identStart | ||
239 | upperLetter = satisfy isUpper <|> ifNoCNamespace identStart | ||
240 | |||
241 | --upperCase, lowerCase, symbols, colonSymbols, backquotedIdent :: P SName | ||
242 | |||
243 | upperCase = identifier (tick' =<< maybeStartWith (=='\'') ((:) <$> upperLetter <*> many identLetter)) <?> "uppercase ident" | 229 | upperCase = identifier (tick' =<< maybeStartWith (=='\'') ((:) <$> upperLetter <*> many identLetter)) <?> "uppercase ident" |
244 | lowerCase = identifier ((:) <$> lowerLetter <*> many identLetter) <?> "lowercase ident" | 230 | lowerCase = identifier ((:) <$> lowerLetter <*> many identLetter) <?> "lowercase ident" |
245 | backquotedIdent = identifier ((:) <$ char '`' <*> identStart <*> many identLetter <* char '`') <?> "backquoted ident" | 231 | backquotedIdent = identifier ((:) <$ char '`' <*> identStart <*> many identLetter <* char '`') <?> "backquoted ident" |
@@ -256,8 +242,6 @@ rhsOperator = symbols <|> backquotedIdent | |||
256 | varId = lowerCase <|> parens (symbols <|> backquotedIdent) | 242 | varId = lowerCase <|> parens (symbols <|> backquotedIdent) |
257 | upperLower = lowerCase <|> upperCase <|> parens symbols | 243 | upperLower = lowerCase <|> upperCase <|> parens symbols |
258 | 244 | ||
259 | --qIdent = {-qualified_ todo-} (lowerCase <|> upperCase) | ||
260 | |||
261 | -------------------------------------------------------------------------------- fixity handling | 245 | -------------------------------------------------------------------------------- fixity handling |
262 | 246 | ||
263 | data FixityDef = Infix | InfixL | InfixR deriving (Show) | 247 | data FixityDef = Infix | InfixL | InfixR deriving (Show) |
diff --git a/src/LambdaCube/Compiler/Parser.hs b/src/LambdaCube/Compiler/Parser.hs index 277f67b1..b52c4cfd 100644 --- a/src/LambdaCube/Compiler/Parser.hs +++ b/src/LambdaCube/Compiler/Parser.hs | |||
@@ -404,7 +404,7 @@ parseTerm_ prec = case prec of | |||
404 | <|> SGlobal <$> lowerCase | 404 | <|> SGlobal <$> lowerCase |
405 | <|> SGlobal <$> upperCase -- todo: move under ppa? | 405 | <|> SGlobal <$> upperCase -- todo: move under ppa? |
406 | <|> braces (mkRecord <$> commaSep ((,) <$> lowerCase <* symbol ":" <*> parseTerm PrecLam)) | 406 | <|> braces (mkRecord <$> commaSep ((,) <$> lowerCase <* symbol ":" <*> parseTerm PrecLam)) |
407 | <|> char '\'' *> ppa (fmap switchNamespace) | 407 | <|> char '\'' *> ppa switchNamespace |
408 | <|> ppa id | 408 | <|> ppa id |
409 | where | 409 | where |
410 | level pr f = parseTerm_ pr >>= \t -> option t $ f t | 410 | level pr f = parseTerm_ pr >>= \t -> option t $ f t |
@@ -413,9 +413,9 @@ parseTerm_ prec = case prec of | |||
413 | brackets ( (parseTerm PrecLam >>= \e -> | 413 | brackets ( (parseTerm PrecLam >>= \e -> |
414 | mkDotDot e <$ reservedOp ".." <*> parseTerm PrecLam | 414 | mkDotDot e <$ reservedOp ".." <*> parseTerm PrecLam |
415 | <|> foldr ($) (SBuiltin "Cons" `SAppV` e `SAppV` SBuiltin "Nil") <$ reservedOp "|" <*> commaSep (generator <|> letdecl <|> boolExpression) | 415 | <|> foldr ($) (SBuiltin "Cons" `SAppV` e `SAppV` SBuiltin "Nil") <$ reservedOp "|" <*> commaSep (generator <|> letdecl <|> boolExpression) |
416 | <|> mkList . tick <$> namespace' <*> ((e:) <$> option [] (symbol "," *> commaSep1 (parseTerm PrecLam))) | 416 | <|> mkList . tick <$> namespace <*> ((e:) <$> option [] (symbol "," *> commaSep1 (parseTerm PrecLam))) |
417 | ) <|> mkList . tick <$> namespace' <*> pure []) | 417 | ) <|> mkList . tick <$> namespace <*> pure []) |
418 | <|> parens (SGlobal <$> try "opname" (symbols <* lookAhead (symbol ")")) <|> mkTuple . tick <$> namespace' <*> commaSep (parseTerm PrecLam)) | 418 | <|> parens (SGlobal <$> try "opname" (symbols <* lookAhead (symbol ")")) <|> mkTuple . tick <$> namespace <*> commaSep (parseTerm PrecLam)) |
419 | 419 | ||
420 | mkSwizzling term = swizzcall | 420 | mkSwizzling term = swizzcall |
421 | where | 421 | where |
@@ -448,15 +448,14 @@ parseTerm_ prec = case prec of | |||
448 | (SBuiltin "HNil") | 448 | (SBuiltin "HNil") |
449 | 449 | ||
450 | mkTuple _ [Section e] = e | 450 | mkTuple _ [Section e] = e |
451 | mkTuple (Just TypeLevel) [Parens e] = SBuiltin "'HList" `SAppV` (SBuiltin "Cons" `SAppV` e `SAppV` SBuiltin "Nil") | 451 | mkTuple ExpNS [Parens e] = SBuiltin "HCons" `SAppV` e `SAppV` SBuiltin "HNil" |
452 | mkTuple _ [Parens e] = SBuiltin "HCons" `SAppV` e `SAppV` SBuiltin "HNil" | 452 | mkTuple TypeNS [Parens e] = SBuiltin "'HList" `SAppV` (SBuiltin "Cons" `SAppV` e `SAppV` SBuiltin "Nil") |
453 | mkTuple _ [x] = Parens x | 453 | mkTuple _ [x] = Parens x |
454 | mkTuple (Just TypeLevel) xs = SBuiltin "'HList" `SAppV` foldr (\x y -> SBuiltin "Cons" `SAppV` x `SAppV` y) (SBuiltin "Nil") xs | 454 | mkTuple ExpNS xs = foldr (\x y -> SBuiltin "HCons" `SAppV` x `SAppV` y) (SBuiltin "HNil") xs |
455 | mkTuple _ xs = foldr (\x y -> SBuiltin "HCons" `SAppV` x `SAppV` y) (SBuiltin "HNil") xs | 455 | mkTuple TypeNS xs = SBuiltin "'HList" `SAppV` foldr (\x y -> SBuiltin "Cons" `SAppV` x `SAppV` y) (SBuiltin "Nil") xs |
456 | 456 | ||
457 | mkList (Just TypeLevel) [x] = SBuiltin "'List" `SAppV` x | 457 | mkList TypeNS [x] = SBuiltin "'List" `SAppV` x |
458 | mkList (Just ExpLevel) xs = foldr (\x l -> SBuiltin "Cons" `SAppV` x `SAppV` l) (SBuiltin "Nil") xs | 458 | mkList _ xs = foldr (\x l -> SBuiltin "Cons" `SAppV` x `SAppV` l) (SBuiltin "Nil") xs |
459 | mkList _ xs = error "mkList" | ||
460 | 459 | ||
461 | mkLit n@LInt{} = SBuiltin "fromInt" `SAppV` sLit n | 460 | mkLit n@LInt{} = SBuiltin "fromInt" `SAppV` sLit n |
462 | mkLit l = sLit l | 461 | mkLit l = sLit l |
@@ -599,7 +598,7 @@ parsePat = \case | |||
599 | where | 598 | where |
600 | litP = flip ViewPat (ParPat [PCon (mempty, "True") []]) . SAppV (SBuiltin "==") | 599 | litP = flip ViewPat (ParPat [PCon (mempty, "True") []]) . SAppV (SBuiltin "==") |
601 | 600 | ||
602 | mkLit (Namespace (Just TypeLevel) _) (LInt n) = toNatP n -- todo: elim this alternative | 601 | mkLit TypeNS (LInt n) = toNatP n -- todo: elim this alternative |
603 | mkLit _ n@LInt{} = litP (SBuiltin "fromInt" `SAppV` sLit n) | 602 | mkLit _ n@LInt{} = litP (SBuiltin "fromInt" `SAppV` sLit n) |
604 | mkLit _ n = litP (sLit n) | 603 | mkLit _ n = litP (sLit n) |
605 | 604 | ||
@@ -612,7 +611,7 @@ parsePat = \case | |||
612 | 611 | ||
613 | patlist = commaSep $ parsePat PrecAnn | 612 | patlist = commaSep $ parsePat PrecAnn |
614 | 613 | ||
615 | mkListPat ns [p] | namespaceLevel ns == Just TypeLevel = PCon (debugSI "mkListPat4", "'List") [ParPat [p]] | 614 | mkListPat TypeNS [p] = PCon (debugSI "mkListPat4", "'List") [ParPat [p]] |
616 | mkListPat ns (p: ps) = PCon (debugSI "mkListPat2", "Cons") $ map (ParPat . (:[])) [p, mkListPat ns ps] | 615 | mkListPat ns (p: ps) = PCon (debugSI "mkListPat2", "Cons") $ map (ParPat . (:[])) [p, mkListPat ns ps] |
617 | mkListPat _ [] = PCon (debugSI "mkListPat3", "Nil") [] | 616 | mkListPat _ [] = PCon (debugSI "mkListPat3", "Nil") [] |
618 | 617 | ||
@@ -918,7 +917,7 @@ mkLets ds = mkLets' . sortDefs ds where | |||
918 | mkLets' (x: ds) e = error $ "mkLets: " ++ show x | 917 | mkLets' (x: ds) e = error $ "mkLets: " ++ show x |
919 | 918 | ||
920 | addForalls :: Up a => Extensions -> [SName] -> SExp' a -> SExp' a | 919 | addForalls :: Up a => Extensions -> [SName] -> SExp' a -> SExp' a |
921 | addForalls exs defined x = foldl f x [v | v@(_, vh:_) <- reverse $ freeS x, snd v `notElem'` ("fromInt"{-todo: remove-}: defined), isLower vh || NoConstructorNamespace `elem` exs] | 920 | addForalls exs defined x = foldl f x [v | v@(_, vh:_) <- reverse $ freeS x, snd v `notElem'` ("fromInt"{-todo: remove-}: defined), isLower vh] |
922 | where | 921 | where |
923 | f e v = SPi Hidden (Wildcard SType) $ substSG0 v e | 922 | f e v = SPi Hidden (Wildcard SType) $ substSG0 v e |
924 | 923 | ||
@@ -1065,8 +1064,6 @@ type Extensions = [Extension] | |||
1065 | 1064 | ||
1066 | data Extension | 1065 | data Extension |
1067 | = NoImplicitPrelude | 1066 | = NoImplicitPrelude |
1068 | | NoTypeNamespace | ||
1069 | | NoConstructorNamespace | ||
1070 | | TraceTypeCheck | 1067 | | TraceTypeCheck |
1071 | deriving (Enum, Eq, Ord, Show) | 1068 | deriving (Enum, Eq, Ord, Show) |
1072 | 1069 | ||
@@ -1099,11 +1096,10 @@ type DefParser = DesugarInfo -> (Either ParseError [Stmt], [PostponedCheck]) | |||
1099 | parseModule :: FilePath -> String -> P Module | 1096 | parseModule :: FilePath -> String -> P Module |
1100 | parseModule f str = do | 1097 | parseModule f str = do |
1101 | exts <- concat <$> many parseExtensions | 1098 | exts <- concat <$> many parseExtensions |
1102 | let ns = Namespace (if NoTypeNamespace `elem` exts then Nothing else Just ExpLevel) (NoConstructorNamespace `notElem` exts) | ||
1103 | whiteSpace | 1099 | whiteSpace |
1104 | header <- optional $ do | 1100 | header <- optional $ do |
1105 | modn <- reserved "module" *> moduleName | 1101 | modn <- reserved "module" *> moduleName |
1106 | exps <- optional (parens $ commaSep $ parseExport ns) | 1102 | exps <- optional (parens $ commaSep $ parseExport ExpNS) |
1107 | reserved "where" | 1103 | reserved "where" |
1108 | return (modn, exps) | 1104 | return (modn, exps) |
1109 | let mkIDef _ n i h _ = (n, f i h) | 1105 | let mkIDef _ n i h _ = (n, f i h) |
@@ -1123,13 +1119,13 @@ parseModule f str = do | |||
1123 | { extensions = exts | 1119 | { extensions = exts |
1124 | , moduleImports = [((mempty, "Prelude"), ImportAllBut []) | NoImplicitPrelude `notElem` exts] ++ idefs | 1120 | , moduleImports = [((mempty, "Prelude"), ImportAllBut []) | NoImplicitPrelude `notElem` exts] ++ idefs |
1125 | , moduleExports = join $ snd <$> header | 1121 | , moduleExports = join $ snd <$> header |
1126 | , definitions = \ge -> first snd $ runP' (ge, ns) f (parseDefs <* eof) st | 1122 | , definitions = \ge -> first snd $ runP' (ge, ExpNS) f (parseDefs <* eof) st |
1127 | } | 1123 | } |
1128 | 1124 | ||
1129 | parseLC :: FilePath -> String -> Either ParseError Module | 1125 | parseLC :: FilePath -> String -> Either ParseError Module |
1130 | parseLC f str | 1126 | parseLC f str |
1131 | = fst | 1127 | = fst |
1132 | . runP (error "globalenv used", Namespace (Just ExpLevel) True) f (parseModule f str) | 1128 | . runP (error "globalenv used", ExpNS) f (parseModule f str) |
1133 | $ str | 1129 | $ str |
1134 | 1130 | ||
1135 | --type DefParser = DesugarInfo -> (Either ParseError [Stmt], [PostponedCheck]) | 1131 | --type DefParser = DesugarInfo -> (Either ParseError [Stmt], [PostponedCheck]) |