(************************************************************************) (* * The Rocq Prover / The Rocq Development Team *) (* v * Copyright INRIA, CNRS and contributors *) (* <O___,, * (see version control and CREDITS file for authors & dates) *) (* \VV/ **************************************************************) (* // * This file is distributed under the terms of the *) (* * GNU Lesser General Public License Version 2.1 *) (* * (see LICENSE file for the text of the license) *) (************************************************************************)
open Rocqlib open CErrors open Util open Termops open EConstr open Retyping open Typing open Inductiveops
module RelDecl = Context.Rel.Declaration
(**************) (** Telescope *)
let get_sigmatypes sigma ~sort ~predsort = letopen EConstr in letopen Sorts.Quality in let which, sigsort = match predsort, sort with
| QConstant QSProp, _ | _, QConstant QSProp ->
user_err Pp.(str "SProp arguments not supported by Program Fixpoint yet.")
| QConstant QProp, QConstant QProp -> "ex", qprop
| QConstant QProp, QConstant QType -> "sig", qtype
| QConstant QType, QConstant (QProp|QType) -> "sigT", qtype
| _ -> assert false in let sigma, ty = Evd.fresh_global (Global.env ()) sigma (lib_ref ("core."^which^".type")) in let uinstance = snd (destRef sigma ty) in let intro = mkRef (lib_ref ("core."^which^".intro"), uinstance) in let p1 = mkRef (lib_ref ("core."^which^".proj1"), uinstance) in let p2 = mkRef (lib_ref ("core."^which^".proj2"), uinstance) in
sigma, ty, intro, p1, p2, sigsort
let rec telescope sigma l = letopen EConstr in letopen Vars in match l with
| [] -> assert false
| [RelDecl.LocalAssum (n, t), _] ->
sigma, t, [RelDecl.LocalDef (n, mkRel 1, t)], mkRel 1
| (LocalAssum (n, t), tsort) :: tl -> let sigma, ty, _tysort, tys, (k, constr) = List.fold_left
(fun (sigma, ty, tysort, tys, (k, constr)) (decl,sort) -> let t = RelDecl.get_type decl in let pred = mkLambda (RelDecl.get_annot decl, t, ty) in let sigma, ty, intro, p1, p2, sigsort = get_sigmatypes sigma ~predsort:tysort ~sort in let sigty = mkApp (ty, [|t; pred|]) in let intro = mkApp (intro, [|lift k t; lift k pred; mkRel k; constr|]) in
(sigma, sigty, sigsort, (pred, p1, p2) :: tys, (succ k, intro)))
(sigma, t, tsort, [], (2, mkRel 1)) tl in let sigma, last, subst = List.fold_right2
(fun (pred,p1,p2) (decl,_) (sigma, prev, subst) -> let t = RelDecl.get_type decl in let proj1 = applist (p1, [t; pred; prev]) in let proj2 = applist (p2, [t; pred; prev]) in
(sigma, lift 1 proj2, RelDecl.(LocalDef (get_annot decl, proj1, t) :: subst)))
(List.rev tys) tl (sigma, mkRel 1, []) in sigma, ty, (LocalDef (n, last, t) :: subst), constr
| (LocalDef (n, b, t), _) :: tl -> let sigma, ty, subst, term = telescope sigma tl in
sigma, ty, (LocalDef (n, b, t) :: subst), lift 1 term
let telescope env sigma ctx = let ctx, _ = List.fold_right_map (fun d env -> let s = Retyping.get_sort_quality_of env sigma (RelDecl.get_type d) in let env = EConstr.push_rel d env in
(d, UnivGen.QualityOrSet.quality s), env) ctx env in let sigma, telescope_type, letcontext, telescope_value = telescope sigma ctx in
sigma, letcontext, { telescope_type; telescope_value }
(****************************************************) (** Closure of a term according to its dependencies *)
(* [make_tuple env sigma (rterm,rty) lind] assumes [lind] is the lesser indexboundin[rty]
let make_tuple env sigma (rterm,rty) lind =
assert (not (Vars.noccurn sigma lind rty)); let sigdata = build_sigma_type () in let sigma, a = type_of ~refresh:true env sigma (mkRel lind) in let a = Tacred.simpl env sigma a in let na = Context.Rel.Declaration.get_annot (lookup_rel lind env) in (* We move [lind] to [1] and lift other rels > [lind] by 1 *) let rty = Vars.lift (1-lind) (Vars.liftn lind (lind+1) rty) in (* Now [lind] is [mkRel 1] and we abstract on (na:a) *) let p = mkLambda (na, a, rty) in let sigma, exist_term = Evd.fresh_global env sigma sigdata.intro in let sigma, sig_term = Evd.fresh_global env sigma sigdata.typ in
sigma,
(applist(exist_term,[a;p;(mkRel lind);rterm]),
applist(sig_term,[a;p]))
(* check that the free-references of the type of [c] are contained in thefree-referencesofthenormal-formofthattype.Strictly computingtheexactsetoffreerelswouldrequirefull normalizationbutthisisnotreasonable(e.g.inpresenceof recordsthatcontainsproofs).Werestrictourselftoa"simpl"
normalization *)
let minimal_free_rels env sigma (c,cty) = let cty_rels = free_rels sigma cty in let cty' = Tacred.simpl env sigma cty in let rels' = free_rels sigma cty'in if Int.Set.subset cty_rels rels' then
(cty,cty_rels) else
(cty',rels')
(* Like the above, but recurse over all the rels found until there are
no more rels to be found *)
let minimal_free_rels_rec env sigma = let rec minimalrec_free_rels_rec prev_rels (c,cty) = let (cty,direct_rels) = minimal_free_rels env sigma (c,cty) in let combined_rels = Int.Set.union prev_rels direct_rels in let folder rels i = snd (minimalrec_free_rels_rec rels (c, get_type_of env sigma (mkRel i))) in (cty, List.fold_left folder combined_rels (Int.Set.elements (Int.Set.diff direct_rels prev_rels))) in minimalrec_free_rels_rec Int.Set.empty
let sig_clausal_form env sigma sort_of_ty siglen ty dflt = let sigdata = build_sigma_type () in let rec sigrec_clausal_form sigma siglen p_i = if Int.equal siglen 0then (* is the default value typable with the expected type *) let dflt_typ = Retyping.get_type_of env sigma dflt in try let sigma = Evarconv.unify_leq_delay env sigma dflt_typ p_i in let sigma = Evarconv.solve_unif_constraints_with_heuristics env sigma in
sigma, dflt with Evarconv.UnableToUnify _ ->
user_err Pp.(str "Cannot solve a unification problem.") else let (a,p_i_minus_1) = match Reductionops.whd_beta_stack env sigma p_i with
| (_sigT,[a;p]) -> (a, p)
| _ -> anomaly ~label:"sig_clausal_form" (Pp.str "should be a sigma type.") in let typeclass_candidate = Typeclasses.is_maybe_class_type sigma a in let sigma, ev = Evarutil.new_evar ~typeclass_candidate env sigma a in let rty = Reductionops.beta_applist sigma (p_i_minus_1,[ev]) in let sigma, tuple_tail = sigrec_clausal_form sigma (siglen-1) rty in if EConstr.isEvar sigma ev then (* This at least happens if what has been detected as a dependencyisnotone;useanevasiveerrormessage; eveniftheproblemisupwards:unificationshouldbe triedinthefirstplaceinmake_iterated_tupleinstead ofapproximativelycomputingthefreerels;then
unsolved evars would mean not binding rel *)
user_err Pp.(str "Cannot solve a unification problem.") else let sigma, exist_term = Evd.fresh_global env sigma sigdata.intro in
sigma, applist(exist_term,[a;p_i_minus_1;ev;tuple_tail]) in let sigma, scf = sigrec_clausal_form sigma siglen ty in
sigma, Evarutil.nf_evar sigma scf
(** [make_iterated_tuple env sigma default c ctype] retruns
let make_iterated_tuple env sigma ~default c cty = let (cty,rels) = minimal_free_rels_rec env sigma (c,cty) in let sort_of_cty = get_sort_of env sigma cty in let sorted_rels = Int.Set.elements rels in let sigma, (telescope_value, telescope_type) = List.fold_left (fun (sigma, t) -> make_tuple env sigma t) (sigma, (c,cty)) sorted_rels in
assert (Vars.closed0 sigma telescope_type); let n = List.length sorted_rels in let sigma, dfltval = sig_clausal_form env sigma sort_of_cty n telescope_type default in
sigma, { telescope_value; telescope_type }, dfltval
(** [make_selector env sigma dirn c ind special default]] constructsacase-spliton[c]oftype[ind],withthe[dirn]-th
branch giving [special], and all the rest giving [default]. *)
let make_selector env sigma ~pos ~special ~default c ctype = let IndType(indf,_) as indt = try find_rectype env sigma ctype with Not_found -> (* one can find Rel(k) in case of dependent constructors likeT:=c:(A:Set)A->Tandadiscrimination on(cbooltrue)=(cboolfalse) CP:changedassertfalseinamoreinformativeerror
*)
user_err
Pp.(str "Cannot discriminate on inductive constructors with \
dependent types.") in let (ind, _),_ = dest_ind_family indf in let () = Tacred.check_privacy env ind in let typ = Retyping.get_type_of env sigma default in let (mib,mip) = Inductive.lookup_mind_specif env ind in let deparsign = make_arity_signature env sigma true indf in let p = it_mkLambda_or_LetIn typ deparsign in let cstrs = get_constructors env indf in let build_branch i = let endpt = if Int.equal i pos then special else default in let args = cstrs.(i-1).cs_args in
it_mkLambda_or_LetIn endpt args in let brl = List.map build_branch(List.interval 1 (Array.length mip.mind_consnames)) in let rci = ERelevance.relevant in(* TODO relevance *) let ci = make_case_info env ind RegularStyle in
Inductiveops.make_case_or_project env sigma indt ci (p, rci) c (Array.of_list brl)
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.