@@ -510,22 +510,30 @@ interpretExpr expr =
510510 SS. Var pos x -> do
511511 avail <- gets rwPrimsAvail
512512 Environ varenv _tyenv <- gets rwEnviron
513- case ScopedMap. lookup x varenv of
514- Nothing ->
515- -- This should be rejected by the typechecker, so panic
516- panic " interpretExpr" [
517- " Read of unknown variable " <> x
518- ]
519- Just (_defpos, lc, _rebindable, _ty, v, _doc)
520- | Set. member lc avail -> do
521- let v' = injectPositionIntoMonadicValue pos v
522- v'' = insertRefChain pos x v'
523- return v''
524- | otherwise ->
525- -- This case is also rejected by the typechecker
526- panic " interpretExpr" [
527- " Read of inaccessible variable " <> x
528- ]
513+ rbenv <- gets rwRebindables
514+ let info = case ScopedMap. lookup x varenv of
515+ Nothing ->
516+ -- Try the rebindable environment
517+ case Map. lookup x rbenv of
518+ Nothing -> Nothing
519+ Just (_defpos, _ty, v) -> Just (Current , v)
520+ Just (_defpos, lc, _ty, v, _doc) -> Just (lc, v)
521+ case info of
522+ Nothing ->
523+ -- This should be rejected by the typechecker; panic
524+ panic " interpretExpr" [
525+ " Read of unknown variable " <> x
526+ ]
527+ Just (lc, v)
528+ | Set. member lc avail -> do
529+ let v' = injectPositionIntoMonadicValue pos v
530+ v'' = insertRefChain pos x v'
531+ return v''
532+ | otherwise ->
533+ -- This case is also rejected by the typechecker
534+ panic " interpretExpr" [
535+ " Read of inaccessible variable " <> x
536+ ]
529537 SS. Lambda _pos mname pat e -> do
530538 env <- gets rwEnviron
531539 return $ VLambda env mname pat e
@@ -912,9 +920,15 @@ interpretTopStmt printBinds stmt = do
912920 -- - shouldn't have to flatten the environments
913921 -- - shouldn't be typechecking one statement at a time regardless
914922 Environ varenv tyenv <- liftTopLevel $ gets rwEnviron
915- let varenv' = Map. map (\ (pos, lc, rb, ty, _v, _doc) -> (pos, lc, rb, ty)) $ ScopedMap. flatten varenv
923+ rbenv <- liftTopLevel $ gets rwRebindables
924+
925+ let varenv' = Map. map (\ (pos, lc, ty, _v, _doc) -> (pos, lc, SS. ReadOnlyVar , ty)) $ ScopedMap. flatten varenv
926+ rbenv' = Map. map (\ (pos, ty, _v) -> (pos, SS. Current , SS. RebindableVar , ty)) rbenv
927+ -- If anything appears in both, favor the real environment
928+ varenv'' = Map. union varenv' rbenv'
929+
916930 let tyenv' = ScopedMap. flatten tyenv
917- stmt' <- processTypeCheck $ checkStmt avail varenv' tyenv' ctx stmt
931+ stmt' <- processTypeCheck $ checkStmt avail varenv'' tyenv' ctx stmt
918932
919933 case stmt' of
920934
@@ -995,6 +1009,7 @@ interpretMain :: TopLevel ()
9951009interpretMain = do
9961010 avail <- gets rwPrimsAvail
9971011 Environ varenv tyenv <- gets rwEnviron
1012+ rbenv <- gets rwRebindables
9981013 let pos = SS. PosInternal " entry"
9991014 -- We need the type to be "TopLevel a", not just "TopLevel ()".
10001015 -- There are several (old) tests in the test suite whose main
@@ -1004,11 +1019,19 @@ interpretMain = do
10041019 tyRet = SS. TyVar pos " a"
10051020 tyMonadic = SS. tBlock pos (SS. tContext pos SS. TopLevel ) tyRet
10061021 tyExpected = SS. Forall [(pos, " a" )] tyMonadic
1007- case ScopedMap. lookup " main" varenv of
1022+ let main = case ScopedMap. lookup " main" varenv of
1023+ Just (_defpos, lc, tyFound, v, _doc) -> Just (lc, tyFound, v)
1024+ -- Having main be rebindable doesn't make much sense, but
1025+ -- it's easier to have this code than to spend time
1026+ -- explaining that it's not allowed.
1027+ Nothing -> case Map. lookup " main" rbenv of
1028+ Nothing -> Nothing
1029+ Just (_defpos, tyFound, v) -> Just (Current , tyFound, v)
1030+ case main of
10081031 Nothing ->
10091032 -- Don't fail or complain if there's no main.
10101033 return ()
1011- Just (_defpos, Current , _rebindable, tyFound, v, _doc ) -> case tyFound of
1034+ Just (Current , tyFound, v) -> case tyFound of
10121035 SS. Forall _ (SS. TyCon _ SS. BlockCon [_, _]) ->
10131036 -- XXX shouldn't have to do this
10141037 let tyenv' = ScopedMap. flatten tyenv in
@@ -1026,7 +1049,7 @@ interpretMain = do
10261049 -- If the type is something entirely random, like a Term or a
10271050 -- String or something, just ignore it.
10281051 return ()
1029- Just (_defpos, lc, _rebindable, _ty, _v, _doc ) ->
1052+ Just (lc, _ty, _v) ->
10301053 -- There is no way for things other than primitives to get marked
10311054 -- experimental or deprecated, so this isn't possible. If we allow
10321055 -- users to deprecate their own functions in the future, change
@@ -1093,6 +1116,7 @@ buildTopLevelEnv proxy opts scriptArgv =
10931116
10941117 let rw0 = TopLevelRW
10951118 { rwEnviron = primEnviron opts bic
1119+ , rwRebindables = Map. empty
10961120 , rwCryptol = ce0
10971121 , rwPosition = SS. Unknown
10981122 , rwStackTrace = Trace. empty
@@ -6455,7 +6479,7 @@ primNamedTypeEnv = fmap extract primTypes
64556479primValueEnv ::
64566480 Options ->
64576481 BuiltinContext ->
6458- Map SS. Name (SS. Pos , PrimitiveLifecycle , SS. Rebindable , SS. Schema , Value , Maybe [Text ])
6482+ Map SS. Name (SS. Pos , PrimitiveLifecycle , SS. Schema , Value , Maybe [Text ])
64596483primValueEnv opts bic = Map. mapWithKey extract primitives
64606484 where
64616485 header = [
@@ -6476,7 +6500,7 @@ primValueEnv opts bic = Map.mapWithKey extract primitives
64766500 header <> tag p <> name n p <> primitiveDoc p
64776501 extract n p =
64786502 let pos = SS. PosInternal " <<builtin>>" in
6479- (pos, primitiveLife p, SS. ReadOnlyVar , primitiveType p,
6503+ (pos, primitiveLife p, primitiveType p,
64806504 (primitiveFn p) opts bic, Just $ doc n p)
64816505
64826506primEnviron :: Options -> BuiltinContext -> Environ
0 commit comments