@@ -12,12 +12,15 @@ module Wingman.Judgements.Theta
12
12
13
13
import Class (classTyVars )
14
14
import Control.Applicative (empty )
15
+ import Control.Lens (preview )
15
16
import Data.Maybe (fromMaybe , mapMaybe , maybeToList )
17
+ import Data.Generics.Sum (_Ctor )
16
18
import Data.Set (Set )
17
19
import qualified Data.Set as S
18
20
import Development.IDE.Core.UseStale
19
21
import Development.IDE.GHC.Compat
20
- import Generics.SYB hiding (tyConName , empty )
22
+ import Generics.SYB hiding (tyConName , empty , Generic )
23
+ import GHC.Generics
21
24
import GhcPlugins (mkVarOcc , splitTyConApp_maybe , getTyVar_maybe , zipTvSubst , unionTCvSubst , emptyTCvSubst , TCvSubst )
22
25
#if __GLASGOW_HASKELL__ > 806
23
26
import GhcPlugins (eqTyCon )
@@ -40,7 +43,7 @@ data Evidence
40
43
= EqualityOfTypes Type Type
41
44
-- | We have an instance in scope
42
45
| HasInstance PredType
43
- deriving (Show )
46
+ deriving (Show , Generic )
44
47
45
48
46
49
------------------------------------------------------------------------------
@@ -75,36 +78,46 @@ getEvidenceAtHole (unTrack -> dst)
75
78
. unTrack
76
79
77
80
78
- ------------------------------------------------------------------------------
79
- -- | Update our knowledge of which types are equal.
80
- hi :: Evidence -> TacticState -> TacticState
81
- hi (EqualityOfTypes a b) ts =
81
+ mkSubst :: Set TyVar -> Type -> Type -> TCvSubst
82
+ mkSubst skolems a b =
82
83
let tyvars = S. fromList $ mapMaybe getTyVar_maybe [a, b]
83
84
-- If we can unify our skolems, at least one is no longer a skolem.
84
85
-- Removing them from this set ensures we can get a subtitution between
85
86
-- the two. But it's okay to leave them in 'ts_skolems' in general, since
86
87
-- they won't exist after running this substitution.
87
- skolems = ts_skolems ts S. \\ tyvars
88
+ skolems' = skolems S. \\ tyvars
88
89
in
89
- case tryUnifyUnivarsButNotSkolems skolems (CType a) (CType b) of
90
- Just subst -> updateSubst subst ts
91
- Nothing -> ts
92
- hi HasInstance {} ts = ts
93
-
94
- substEvidence :: TCvSubst -> Evidence -> Evidence
95
- substEvidence subst (EqualityOfTypes ty ty') =
96
- EqualityOfTypes (substTy subst ty) (substTy subst ty')
97
- substEvidence _ x = x
98
-
99
- allEvidenceToSubst :: [Evidence ] -> TCvSubst
100
- allEvidenceToSubst [] = emptyTCvSubst
101
- allEvidenceToSubst (HasInstance {} : evs) = allEvidenceToSubst evs
102
- allEvidenceToSubst (eq@ EqualityOfTypes {} : evs) =
103
- let subst = ts_unifier $ hi eq defaultTacticState
104
- in unionTCvSubst subst $ allEvidenceToSubst $ fmap (substEvidence subst) evs
90
+ case tryUnifyUnivarsButNotSkolems skolems' (CType a) (CType b) of
91
+ Just subst -> subst
92
+ Nothing -> emptyTCvSubst
93
+
94
+
95
+ substPair :: TCvSubst -> (Type , Type ) -> (Type , Type )
96
+ substPair subst (ty, ty') = (substTy subst ty, substTy subst ty')
97
+
105
98
99
+ ------------------------------------------------------------------------------
100
+ -- | Construct a substitution given a list of types that are equal to one
101
+ -- another. This is more subtle than it seems, since there might be several
102
+ -- equalities for the same type. We must be careful to push the accumulating
103
+ -- substitution through each pair of types before adding their equalities.
104
+ allEvidenceToSubst :: Set TyVar -> [(Type , Type )] -> TCvSubst
105
+ allEvidenceToSubst _ [] = emptyTCvSubst
106
+ allEvidenceToSubst skolems ((a, b) : evs) =
107
+ let subst = mkSubst skolems a b
108
+ in unionTCvSubst subst
109
+ $ allEvidenceToSubst skolems
110
+ $ fmap (substPair subst) evs
111
+
112
+ ------------------------------------------------------------------------------
113
+ -- | Update our knowledge of which types are equal.
106
114
evidenceToSubst :: [Evidence ] -> TacticState -> TacticState
107
- evidenceToSubst = updateSubst . allEvidenceToSubst
115
+ evidenceToSubst evs ts =
116
+ updateSubst
117
+ (allEvidenceToSubst (ts_skolems ts)
118
+ $ mapMaybe (preview $ _Ctor @ " EqualityOfTypes" )
119
+ $ evs)
120
+ ts
108
121
109
122
110
123
------------------------------------------------------------------------------
0 commit comments