-
Notifications
You must be signed in to change notification settings - Fork 11
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
forbid kind loops #251
base: main
Are you sure you want to change the base?
forbid kind loops #251
Changes from all commits
9373076
16e2cec
b80f2e9
2d9915d
77d1889
75e7928
897dff9
ca74546
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
Infinite kind detected: | ||
(KindVar 55708) = (META(KindVar 55708) → META(KindVar 55701)) |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
#lang "prelude.kl" | ||
|
||
(datatype (Phantom A) | ||
(mk-phantom)) | ||
|
||
-- causes the kind equality ?1 ~ ?2 to be unified twice, which previously | ||
-- caused ?2 to point to itself, thus causing zonking ?2 to run forever. | ||
-- should be accepted. | ||
(example | ||
(with-unknown-type [A] | ||
(the (Phantom A) | ||
(mk-phantom)))) | ||
|
||
-- causes the kind equality ?1 ~ (-> ?1 *). | ||
-- should be accepted by the occurs-check. | ||
(datatype (InfiniteKind A) | ||
(mk-infinite-kind (Phantom (A A)))) |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
Infinite type detected: (MetaPtr 57868) = (List META(MetaPtr 57868)) |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,13 @@ | ||
#lang "prelude.kl" | ||
|
||
-- accepted, thanks to let-generalization | ||
(example | ||
(let [xs (nil)] | ||
(:: xs -- (the (List A) xs) | ||
xs -- (the (List (List A)) xs) | ||
))) | ||
|
||
-- causes the type equality ?1 ~ List ?1, which must be rejected by the | ||
-- occurs-check. | ||
(defun infinite-type (xs) | ||
(:: xs xs)) |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -81,6 +81,7 @@ library | |
PartialType | ||
Phase | ||
Pretty | ||
Pretty.Renumber | ||
Scope | ||
ScopeSet | ||
ShortShow | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -410,7 +410,7 @@ | |
[ ( "open-syntax" | ||
, Scheme [] $ tFun [tSyntax] (Prims.primitiveDatatype "Syntax-Contents" [tSyntax]) | ||
, ValueClosure $ HO $ | ||
\(ValueSyntax stx) -> | ||
Check warning on line 413 in src/Expander.hs GitHub Actions / ubuntu-latest / ghc 9.2.5
Check warning on line 413 in src/Expander.hs GitHub Actions / ubuntu-latest / ghc 9.4
Check warning on line 413 in src/Expander.hs GitHub Actions / ubuntu-latest / ghc 9.6
|
||
case syntaxE stx of | ||
Id name -> | ||
primitiveCtor "identifier-contents" [ValueString name] | ||
|
@@ -428,9 +428,9 @@ | |
, Scheme [] $ | ||
tFun [tSyntax, tSyntax, Prims.primitiveDatatype "Syntax-Contents" [tSyntax]] tSyntax | ||
, ValueClosure $ HO $ | ||
\(ValueSyntax locStx) -> | ||
Check warning on line 431 in src/Expander.hs GitHub Actions / ubuntu-latest / ghc 9.2.5
Check warning on line 431 in src/Expander.hs GitHub Actions / ubuntu-latest / ghc 9.4
Check warning on line 431 in src/Expander.hs GitHub Actions / ubuntu-latest / ghc 9.6
|
||
ValueClosure $ HO $ | ||
\(ValueSyntax scopesStx) -> | ||
Check warning on line 433 in src/Expander.hs GitHub Actions / ubuntu-latest / ghc 9.2.5
Check warning on line 433 in src/Expander.hs GitHub Actions / ubuntu-latest / ghc 9.4
Check warning on line 433 in src/Expander.hs GitHub Actions / ubuntu-latest / ghc 9.6
|
||
ValueClosure $ HO $ | ||
-- N.B. Assuming correct constructors | ||
\(ValueCtor ctor [arg]) -> | ||
|
@@ -544,15 +544,17 @@ | |
| (name, fun) <- [("<", (<)), ("<=", (<=)), (">", (>)), (">=", (>=)), ("=", (==)), ("/=", (/=))] | ||
] ++ | ||
[ ("pure-IO" | ||
, Scheme [KStar, KStar] $ tFun [tSchemaVar 0 []] (tIO (tSchemaVar 0 [])) | ||
, let a = tSchemaVar firstSchemeVar [] | ||
in Scheme [KStar, KStar] $ tFun [a] (tIO a) | ||
, ValueClosure $ HO $ \v -> ValueIOAction (pure v) | ||
) | ||
, ("bind-IO" | ||
, Scheme [KStar, KStar] $ | ||
tFun [ tIO (tSchemaVar 0 []) | ||
, tFun [tSchemaVar 0 []] (tIO (tSchemaVar 1 [])) | ||
] | ||
(tIO (tSchemaVar 1 [])) | ||
, let a:b:_ = [tSchemaVar i [] | i <- [firstSchemeVar..]] | ||
in Scheme [KStar, KStar] $ | ||
tFun [ tIO a | ||
, tFun [a] (tIO b) | ||
] | ||
(tIO b) | ||
, ValueClosure $ HO $ \(ValueIOAction mx) -> do | ||
ValueClosure $ HO $ \(ValueClosure f) -> do | ||
ValueIOAction $ do | ||
|
@@ -596,22 +598,25 @@ | |
, ("Unit", [], [("unit", [])]) | ||
, ("Bool", [], [("true", []), ("false", [])]) | ||
, ("Problem", [], [("module", []), ("declaration", []), ("type", []), ("expression", [tType]), ("pattern", []), ("type-pattern", [])]) | ||
, ("Maybe", [KStar], [("nothing", []), ("just", [tSchemaVar 0 []])]) | ||
, ("List" | ||
, [KStar] | ||
, [ ("nil", []) | ||
, ("::", [tSchemaVar 0 [], Prims.primitiveDatatype "List" [tSchemaVar 0 []]]) | ||
] | ||
) | ||
, let a = tSchemaVar firstSchemeVar [] | ||
in ("Maybe", [KStar], [("nothing", []), ("just", [a])]) | ||
, let a = tSchemaVar firstSchemeVar [] | ||
Comment on lines
+602
to
+603
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Potential type variable conflict due to reuse of The type variable Consider using a mechanism to generate fresh type variable indices for each new type variable. For example: - , let a = tSchemaVar firstSchemeVar []
+ , let a = tSchemaVar nextSchemeVar [] Ensure that
|
||
in ("List" | ||
, [KStar] | ||
, [ ("nil", []) | ||
, ("::", [a, Prims.primitiveDatatype "List" [a]]) | ||
] | ||
) | ||
Comment on lines
+604
to
+609
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Potential type variable conflict due to reuse of Similar to the issue above, in the definition of Consider generating fresh type variables for each new type. For example: - , let a = tSchemaVar firstSchemeVar []
+ , let a = tSchemaVar nextSchemeVar [] Where
|
||
, ("Syntax-Contents" | ||
, [KStar] | ||
, [ ("list-contents", [Prims.primitiveDatatype "List" [tSchemaVar 0 []]]) | ||
, ("integer-contents", [tInteger]) | ||
, ("string-contents", [tString]) | ||
, ("identifier-contents", [tString]) | ||
-- if you add a constructor here, remember to also add a | ||
-- corresponding pattern in close-syntax! | ||
] | ||
, let a = tSchemaVar firstSchemeVar [] | ||
in [ ("list-contents", [Prims.primitiveDatatype "List" [a]]) | ||
, ("integer-contents", [tInteger]) | ||
, ("string-contents", [tString]) | ||
, ("identifier-contents", [tString]) | ||
-- if you add a constructor here, remember to also add a | ||
-- corresponding pattern in close-syntax! | ||
] | ||
Comment on lines
+612
to
+619
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Potential type variable conflict due to reuse of In the definition of Modify the code to use a fresh type variable: - , let a = tSchemaVar firstSchemeVar []
+ , let a = tSchemaVar nextSchemeVar [] Again,
|
||
) | ||
] | ||
|
||
|
@@ -1211,8 +1216,9 @@ | |
case prob of | ||
ExprDest t dest -> do | ||
argTys <- traverse makeTypeMeta argKinds | ||
let tyStore = S.fromList $ zip [firstSchemeVar..] argTys | ||
unify dest t $ tDatatype dt argTys | ||
args' <- for args \a -> inst dest (Scheme argKinds a) argTys | ||
args' <- for args \a -> inst dest (Scheme argKinds a) tyStore | ||
Comment on lines
+1219
to
+1221
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Ensure uniqueness of type variable indices in In constructing Consider maintaining a separate type variable index or using a function to generate fresh type variables to guarantee uniqueness. |
||
Stx _ _ (foundName, foundArgs) <- mustBeCons stx | ||
_ <- mustBeIdent foundName | ||
argDests <- | ||
|
@@ -1225,8 +1231,9 @@ | |
PatternDest patTy dest -> do | ||
Stx _ loc (_cname, subPats) <- mustBeCons stx | ||
tyArgs <- traverse makeTypeMeta argKinds | ||
let tyStore = S.fromList $ zip [firstSchemeVar..] tyArgs | ||
argTypes <- for args \ a -> | ||
inst loc (Scheme argKinds a) tyArgs | ||
inst loc (Scheme argKinds a) tyStore | ||
Comment on lines
+1234
to
+1236
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Ensure uniqueness of type variable indices when instantiating types When instantiating argument types with Adjust the - let tyStore = S.fromList $ zip [firstSchemeVar..] tyArgs
+ let tyStore = S.fromList $ zip [nextSchemeVar..] tyArgs Where
|
||
unify loc (tDatatype dt tyArgs) patTy | ||
if length subPats /= length argTypes | ||
then throwError $ WrongArgCount stx ctor (length argTypes) (length subPats) | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Incorrect number of kind annotations in
pure-IO
function definitionIn the definition of
pure-IO
, theScheme
is given a kind list[KStar, KStar]
, but only one type variablea
is introduced. The number of kinds in the kind list should match the number of type variables.Apply this diff to fix the issue:
📝 Committable suggestion