aboutsummaryrefslogtreecommitdiffhomepage
path: root/pretyping/inductiveops.ml
diff options
context:
space:
mode:
Diffstat (limited to 'pretyping/inductiveops.ml')
-rw-r--r--pretyping/inductiveops.ml62
1 files changed, 49 insertions, 13 deletions
diff --git a/pretyping/inductiveops.ml b/pretyping/inductiveops.ml
index f73f84118..df0b53e9c 100644
--- a/pretyping/inductiveops.ml
+++ b/pretyping/inductiveops.ml
@@ -694,6 +694,43 @@ let infer_inductive_subtyping_arity_constructor
let last_contexts = Context.Rel.fold_outside infer_typ typs ~init:(env, evd, csts) in
if not is_arity then basic_check last_contexts codom else last_contexts
+type ukind =
+ Global | Orig of int | New of int
+
+let make_variance uctx lmap csts =
+ let variance = Array.init (UContext.size uctx) (fun _ -> Variance.Irrelevant) in
+ let geti = Array.fold_left_i (fun i geti u -> LMap.add u i geti)
+ LMap.empty (Instance.to_array @@ UContext.instance uctx)
+ in
+ let lmap_rev = LMap.fold (fun u v lmap_rev -> LMap.add v u lmap_rev) lmap LMap.empty in
+ let analyse_univ u =
+ match LMap.find u lmap_rev with
+ | exception Not_found ->
+ begin match LMap.find u lmap with
+ | exception Not_found -> Global
+ | _ -> Orig (LMap.find u geti)
+ end
+ | uorig -> New (LMap.find uorig geti)
+ in
+ Constraint.iter (fun (l,d,r) ->
+ match analyse_univ l, analyse_univ r with
+ | Orig i, New j when Int.equal i j ->
+ begin match d with
+ | Lt -> anomaly ~label:"make_variance" Pp.(str "unexpected orig < new constraint")
+ | Eq -> variance.(i) <- Variance.sup variance.(i) Variance.Invariant
+ | Le -> variance.(i) <- Variance.sup variance.(i) Variance.Covariant
+ end
+ | New i, Orig j when Int.equal i j ->
+ begin match d with
+ | Lt -> anomaly ~label:"make_variance" Pp.(str "unexpected orig > new constraint")
+ | Eq -> variance.(i) <- Variance.sup variance.(i) Variance.Invariant
+ | Le -> anomaly ~label:"make_variance" Pp.(str "unexpected orig >= new constraint")
+ end
+ | (Global | Orig _ | New _), _ ->
+ anomaly ~label:"make_variance" Pp.(str "unexpected constraint between non copy universes")
+ ) csts;
+ variance
+
let infer_inductive_subtyping env evd mind_ent =
let { Entries.mind_entry_params = params;
Entries.mind_entry_inds = entries;
@@ -706,22 +743,23 @@ let infer_inductive_subtyping env evd mind_ent =
| Entries.Polymorphic_ind_entry _ -> ground_univs
| Entries.Cumulative_ind_entry cumi ->
begin
- let uctx = Univ.CumulativityInfo.univ_context cumi in
- let sbsubst = Univ.CumulativityInfo.subtyping_subst cumi in
- let dosubst = subst_univs_level_constr sbsubst in
- let instance_other =
- Univ.subst_univs_level_instance sbsubst (Univ.UContext.instance uctx)
+ let uctx = CumulativityInfo.univ_context cumi in
+ let new_levels = Array.init (UContext.size uctx) (Level.make DirPath.empty) in
+ let lmap = Array.fold_left2 (fun lmap u u' -> LMap.add u u' lmap)
+ LMap.empty (Instance.to_array @@ UContext.instance uctx) new_levels
in
+ let dosubst = subst_univs_level_constr lmap in
+ let instance_other = Instance.of_array new_levels in
let constraints_other =
Univ.subst_univs_level_constraints
- sbsubst (Univ.UContext.constraints uctx)
+ lmap (Univ.UContext.constraints uctx)
in
let uctx_other = Univ.UContext.make (instance_other, constraints_other) in
let env = Environ.push_context uctx env in
let env = Environ.push_context uctx_other env in
let evd =
- Evd.merge_universe_context
- evd (UState.of_context_set (Univ.ContextSet.of_context uctx_other))
+ Evd.merge_context_set UState.UnivRigid
+ evd (Univ.ContextSet.of_context uctx_other)
in
let (_, _, subtyp_constraints) =
List.fold_left
@@ -737,12 +775,10 @@ let infer_inductive_subtyping env evd mind_ent =
)
ctxs' indentry.Entries.mind_entry_lc
) (env, evd, Univ.Constraint.empty) entries
- in
+ in
+ let variance = make_variance uctx lmap subtyp_constraints in
Entries.Cumulative_ind_entry
(Univ.CumulativityInfo.make
- (Univ.CumulativityInfo.univ_context cumi,
- Univ.UContext.make
- (Univ.UContext.instance (Univ.CumulativityInfo.subtyp_context cumi),
- subtyp_constraints)))
+ (uctx, variance))
end
in {mind_ent with Entries.mind_entry_universes = uinfind;}