]> matita.cs.unibo.it Git - helm.git/blobdiff - helm/ocaml/cic_proof_checking/cicTypeChecker.ml
This commit was manufactured by cvs2svn to create branch
[helm.git] / helm / ocaml / cic_proof_checking / cicTypeChecker.ml
diff --git a/helm/ocaml/cic_proof_checking/cicTypeChecker.ml b/helm/ocaml/cic_proof_checking/cicTypeChecker.ml
deleted file mode 100644 (file)
index 48d8b2e..0000000
+++ /dev/null
@@ -1,1785 +0,0 @@
-(* Copyright (C) 2000, HELM Team.
- * 
- * This file is part of HELM, an Hypertextual, Electronic
- * Library of Mathematics, developed at the Computer Science
- * Department, University of Bologna, Italy.
- * 
- * HELM is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- * 
- * HELM is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with HELM; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place - Suite 330, Boston,
- * MA  02111-1307, USA.
- * 
- * For details, see the HELM World-Wide-Web page,
- * http://cs.unibo.it/helm/.
- *)
-
-type type_checker_exn =
-   Impossible of int
- | NotWellTyped of string
- | WrongUriToConstant of string
- | WrongUriToVariable of string
- | WrongUriToMutualInductiveDefinitions of string
- | ListTooShort
- | NotPositiveOccurrences of string
- | NotWellFormedTypeOfInductiveConstructor of string
- | WrongRequiredArgument of string
- | RelToHiddenHypothesis
- | MetasenvInconsistency;;
-
-(* This is the only exception that will be raised *)
-exception TypeCheckerFailure of type_checker_exn;;
-
-let fdebug = ref 0;;
-let debug t context =
- let rec debug_aux t i =
-  let module C = Cic in
-  let module U = UriManager in
-   CicPp.ppobj (C.Variable ("DEBUG", None, t, [])) ^ "\n" ^ i
- in
-  if !fdebug = 0 then
-   raise
-    (TypeCheckerFailure
-      (NotWellTyped ("\n" ^ List.fold_right debug_aux (t::context) "")))
-   (*print_endline ("\n" ^ List.fold_right debug_aux (t::context) "") ; flush stdout*)
-;;
-
-let rec split l n =
- match (l,n) with
-    (l,0) -> ([], l)
-  | (he::tl, n) -> let (l1,l2) = split tl (n-1) in (he::l1,l2)
-  | (_,_) -> raise (TypeCheckerFailure ListTooShort)
-;;
-
-let debrujin_constructor uri number_of_types =
- let rec aux k =
-  let module C = Cic in
-   function
-      C.Rel n as t when n <= k -> t
-    | C.Rel _ ->
-        raise (TypeCheckerFailure (NotWellTyped ("Debrujin: open term found")))
-    | C.Var (uri,exp_named_subst) ->
-       let exp_named_subst' = 
-        List.map (function (uri,t) -> (uri,aux k t)) exp_named_subst
-       in
-        C.Var (uri,exp_named_subst')
-    | C.Meta _ -> assert false
-    | C.Sort _
-    | C.Implicit as t -> t
-    | C.Cast (te,ty) -> C.Cast (aux k te, aux k ty)
-    | C.Prod (n,s,t) -> C.Prod (n, aux k s, aux (k+1) t)
-    | C.Lambda (n,s,t) -> C.Lambda (n, aux k s, aux (k+1) t)
-    | C.LetIn (n,s,t) -> C.LetIn (n, aux k s, aux (k+1) t)
-    | C.Appl l -> C.Appl (List.map (aux k) l)
-    | C.Const (uri,exp_named_subst) ->
-       let exp_named_subst' = 
-        List.map (function (uri,t) -> (uri,aux k t)) exp_named_subst
-       in
-        C.Const (uri,exp_named_subst')
-    | C.MutInd (uri',tyno,exp_named_subst) when UriManager.eq uri uri' ->
-       if exp_named_subst != [] then
-        raise
-         (TypeCheckerFailure
-           (NotWellTyped
-            ("Debrujin: a non-empty explicit named substitution is applied to "^
-             "a mutual inductive type which is being defined"))) ;
-       C.Rel (k + number_of_types - tyno) ;
-    | C.MutInd (uri',tyno,exp_named_subst) ->
-       let exp_named_subst' = 
-        List.map (function (uri,t) -> (uri,aux k t)) exp_named_subst
-       in
-        C.MutInd (uri',tyno,exp_named_subst')
-    | C.MutConstruct (uri,tyno,consno,exp_named_subst) ->
-       let exp_named_subst' = 
-        List.map (function (uri,t) -> (uri,aux k t)) exp_named_subst
-       in
-        C.MutConstruct (uri,tyno,consno,exp_named_subst')
-    | C.MutCase (sp,i,outty,t,pl) ->
-       C.MutCase (sp, i, aux k outty, aux k t,
-        List.map (aux k) pl)
-    | C.Fix (i, fl) ->
-       let len = List.length fl in
-       let liftedfl =
-        List.map
-         (fun (name, i, ty, bo) -> (name, i, aux k ty, aux (k+len) bo))
-          fl
-       in
-        C.Fix (i, liftedfl)
-    | C.CoFix (i, fl) ->
-       let len = List.length fl in
-       let liftedfl =
-        List.map
-         (fun (name, ty, bo) -> (name, aux k ty, aux (k+len) bo))
-          fl
-       in
-        C.CoFix (i, liftedfl)
- in
-  aux 0
-;;
-
-exception CicEnvironmentError;;
-
-let rec type_of_constant uri =
- let module C = Cic in
- let module R = CicReduction in
- let module U = UriManager in
-  let cobj =
-   match CicEnvironment.is_type_checked ~trust:true uri with
-      CicEnvironment.CheckedObj cobj -> cobj
-    | CicEnvironment.UncheckedObj uobj ->
-       Logger.log (`Start_type_checking uri) ;
-       (* let's typecheck the uncooked obj *)
-       (match uobj with
-           C.Constant (_,Some te,ty,_) ->
-             let _ = type_of ty in
-              if not (R.are_convertible [] (type_of te) ty) then
-               raise
-                (TypeCheckerFailure
-                  (NotWellTyped ("Constant " ^ (U.string_of_uri uri))))
-         | C.Constant (_,None,ty,_) ->
-           (* only to check that ty is well-typed *)
-           let _ = type_of ty in ()
-         | C.CurrentProof (_,conjs,te,ty,_) ->
-             let _ =
-              List.fold_left
-               (fun metasenv ((_,context,ty) as conj) ->
-                 ignore (type_of_aux' metasenv context ty) ;
-                 metasenv @ [conj]
-               ) [] conjs
-             in
-              let _ = type_of_aux' conjs [] ty in
-               if not (R.are_convertible [] (type_of_aux' conjs [] te) ty)
-               then
-                raise
-                 (TypeCheckerFailure
-                   (NotWellTyped ("CurrentProof" ^ (U.string_of_uri uri))))
-         | _ ->
-           raise (TypeCheckerFailure (WrongUriToConstant (U.string_of_uri uri)))
-       ) ;
-       CicEnvironment.set_type_checking_info uri ;
-       Logger.log (`Type_checking_completed uri) ;
-       match CicEnvironment.is_type_checked ~trust:false uri with
-          CicEnvironment.CheckedObj cobj -> cobj
-        | CicEnvironment.UncheckedObj _ -> raise CicEnvironmentError
-  in
-   match cobj with
-      C.Constant (_,_,ty,_) -> ty
-    | C.CurrentProof (_,_,_,ty,_) -> ty
-    | _ -> raise (TypeCheckerFailure (WrongUriToConstant (U.string_of_uri uri)))
-
-and type_of_variable uri =
- let module C = Cic in
- let module R = CicReduction in
- let module U = UriManager in
-  (* 0 because a variable is never cooked => no partial cooking at one level *)
-  match CicEnvironment.is_type_checked ~trust:true uri with
-     CicEnvironment.CheckedObj (C.Variable (_,_,ty,_)) -> ty
-   | CicEnvironment.UncheckedObj (C.Variable (_,bo,ty,_)) ->
-      Logger.log (`Start_type_checking uri) ;
-      (* only to check that ty is well-typed *)
-      let _ = type_of ty in
-       (match bo with
-           None -> ()
-         | Some bo ->
-            if not (R.are_convertible [] (type_of bo) ty) then
-             raise
-              (TypeCheckerFailure
-                (NotWellTyped ("Variable " ^ (U.string_of_uri uri))))
-       ) ;
-       CicEnvironment.set_type_checking_info uri ;
-       Logger.log (`Type_checking_completed uri) ;
-       ty
-   |  _ ->
-       raise
-        (TypeCheckerFailure (WrongUriToVariable (UriManager.string_of_uri uri)))
-
-and does_not_occur context n nn te =
- let module C = Cic in
-   (*CSC: whd sembra essere superflua perche' un caso in cui l'occorrenza *)
-   (*CSC: venga mangiata durante la whd sembra presentare problemi di *)
-   (*CSC: universi                                                    *)
-   match CicReduction.whd context te with
-      C.Rel m when m > n && m <= nn -> false
-    | C.Rel _
-    | C.Meta _
-    | C.Sort _
-    | C.Implicit -> true
-    | C.Cast (te,ty) ->
-       does_not_occur context n nn te && does_not_occur context n nn ty
-    | C.Prod (name,so,dest) ->
-       does_not_occur context n nn so &&
-        does_not_occur((Some (name,(C.Decl so)))::context) (n + 1) (nn + 1) dest
-    | C.Lambda (name,so,dest) ->
-       does_not_occur context n nn so &&
-        does_not_occur((Some (name,(C.Decl so)))::context) (n + 1) (nn + 1) dest
-    | C.LetIn (name,so,dest) ->
-       does_not_occur context n nn so &&
-        does_not_occur ((Some (name,(C.Def so)))::context) (n + 1) (nn + 1) dest
-    | C.Appl l ->
-       List.fold_right (fun x i -> i && does_not_occur context n nn x) l true
-    | C.Var (_,exp_named_subst)
-    | C.Const (_,exp_named_subst)
-    | C.MutInd (_,_,exp_named_subst)
-    | C.MutConstruct (_,_,_,exp_named_subst) ->
-       List.fold_right (fun (_,x) i -> i && does_not_occur context n nn x)
-        exp_named_subst true
-    | C.MutCase (_,_,out,te,pl) ->
-       does_not_occur context n nn out && does_not_occur context n nn te &&
-        List.fold_right (fun x i -> i && does_not_occur context n nn x) pl true
-    | C.Fix (_,fl) ->
-       let len = List.length fl in
-        let n_plus_len = n + len in
-        let nn_plus_len = nn + len in
-        let tys =
-         List.map (fun (n,_,ty,_) -> Some (C.Name n,(Cic.Decl ty))) fl
-        in
-         List.fold_right
-          (fun (_,_,ty,bo) i ->
-            i && does_not_occur context n nn ty &&
-            does_not_occur (tys @ context) n_plus_len nn_plus_len bo
-          ) fl true
-    | C.CoFix (_,fl) ->
-       let len = List.length fl in
-        let n_plus_len = n + len in
-        let nn_plus_len = nn + len in
-        let tys =
-         List.map (fun (n,ty,_) -> Some (C.Name n,(Cic.Decl ty))) fl
-        in
-         List.fold_right
-          (fun (_,ty,bo) i ->
-            i && does_not_occur context n nn ty &&
-            does_not_occur (tys @ context) n_plus_len nn_plus_len bo
-          ) fl true
-
-(*CSC l'indice x dei tipi induttivi e' t.c. n < x <= nn *)
-(*CSC questa funzione e' simile alla are_all_occurrences_positive, ma fa *)
-(*CSC dei controlli leggermente diversi. Viene invocata solamente dalla  *)
-(*CSC strictly_positive                                                  *)
-(*CSC definizione (giusta???) tratta dalla mail di Hugo ;-)              *)
-and weakly_positive context n nn uri te =
- let module C = Cic in
-(*CSC: Che schifo! Bisogna capire meglio e trovare una soluzione ragionevole!*)
-  let dummy_mutind =
-   C.MutInd (UriManager.uri_of_string "cic:/Coq/Init/Datatypes/nat.ind",0,[])
-  in
-  (*CSC mettere in cicSubstitution *)
-  let rec subst_inductive_type_with_dummy_mutind =
-   function
-      C.MutInd (uri',0,_) when UriManager.eq uri' uri ->
-       dummy_mutind
-    | C.Appl ((C.MutInd (uri',0,_))::tl) when UriManager.eq uri' uri ->
-       dummy_mutind
-    | C.Cast (te,ty) -> subst_inductive_type_with_dummy_mutind te
-    | C.Prod (name,so,ta) ->
-       C.Prod (name, subst_inductive_type_with_dummy_mutind so,
-        subst_inductive_type_with_dummy_mutind ta)
-    | C.Lambda (name,so,ta) ->
-       C.Lambda (name, subst_inductive_type_with_dummy_mutind so,
-        subst_inductive_type_with_dummy_mutind ta)
-    | C.Appl tl ->
-       C.Appl (List.map subst_inductive_type_with_dummy_mutind tl)
-    | C.MutCase (uri,i,outtype,term,pl) ->
-       C.MutCase (uri,i,
-        subst_inductive_type_with_dummy_mutind outtype,
-        subst_inductive_type_with_dummy_mutind term,
-        List.map subst_inductive_type_with_dummy_mutind pl)
-    | C.Fix (i,fl) ->
-       C.Fix (i,List.map (fun (name,i,ty,bo) -> (name,i,
-        subst_inductive_type_with_dummy_mutind ty,
-        subst_inductive_type_with_dummy_mutind bo)) fl)
-    | C.CoFix (i,fl) ->
-       C.CoFix (i,List.map (fun (name,ty,bo) -> (name,
-        subst_inductive_type_with_dummy_mutind ty,
-        subst_inductive_type_with_dummy_mutind bo)) fl)
-    | C.Const (uri,exp_named_subst) ->
-       let exp_named_subst' =
-        List.map
-         (function (uri,t) -> (uri,subst_inductive_type_with_dummy_mutind t))
-         exp_named_subst
-       in
-        C.Const (uri,exp_named_subst')
-    | C.MutInd (uri,typeno,exp_named_subst) ->
-       let exp_named_subst' =
-        List.map
-         (function (uri,t) -> (uri,subst_inductive_type_with_dummy_mutind t))
-         exp_named_subst
-       in
-        C.MutInd (uri,typeno,exp_named_subst')
-    | C.MutConstruct (uri,typeno,consno,exp_named_subst) ->
-       let exp_named_subst' =
-        List.map
-         (function (uri,t) -> (uri,subst_inductive_type_with_dummy_mutind t))
-         exp_named_subst
-       in
-        C.MutConstruct (uri,typeno,consno,exp_named_subst')
-    | t -> t
-  in
-  match CicReduction.whd context te with
-     C.Appl ((C.MutInd (uri',0,_))::tl) when UriManager.eq uri' uri -> true
-   | C.MutInd (uri',0,_) when UriManager.eq uri' uri -> true
-   | C.Prod (C.Anonymous,source,dest) ->
-      strictly_positive context n nn
-       (subst_inductive_type_with_dummy_mutind source) &&
-       weakly_positive ((Some (C.Anonymous,(C.Decl source)))::context)
-        (n + 1) (nn + 1) uri dest
-   | C.Prod (name,source,dest) when
-      does_not_occur ((Some (name,(C.Decl source)))::context) 0 n dest ->
-       (* dummy abstraction, so we behave as in the anonimous case *)
-       strictly_positive context n nn
-        (subst_inductive_type_with_dummy_mutind source) &&
-        weakly_positive ((Some (name,(C.Decl source)))::context)
-         (n + 1) (nn + 1) uri dest
-   | C.Prod (name,source,dest) ->
-      does_not_occur context n nn
-       (subst_inductive_type_with_dummy_mutind source)&&
-       weakly_positive ((Some (name,(C.Decl source)))::context)
-        (n + 1) (nn + 1) uri dest
-   | _ ->
-     raise
-      (TypeCheckerFailure
-        (NotWellFormedTypeOfInductiveConstructor
-          ("Guess where the error is ;-)")))
-
-(* instantiate_parameters ps (x1:T1)...(xn:Tn)C                             *)
-(* returns ((x_|ps|:T_|ps|)...(xn:Tn)C){ps_1 / x1 ; ... ; ps_|ps| / x_|ps|} *)
-and instantiate_parameters params c =
- let module C = Cic in
-  match (c,params) with
-     (c,[]) -> c
-   | (C.Prod (_,_,ta), he::tl) ->
-       instantiate_parameters tl
-        (CicSubstitution.subst he ta)
-   | (C.Cast (te,_), _) -> instantiate_parameters params te
-   | (t,l) -> raise (TypeCheckerFailure (Impossible 1))
-
-and strictly_positive context n nn te =
- let module C = Cic in
- let module U = UriManager in
-  match CicReduction.whd context te with
-     C.Rel _ -> true
-   | C.Cast (te,ty) ->
-      (*CSC: bisogna controllare ty????*)
-      strictly_positive context n nn te
-   | C.Prod (name,so,ta) ->
-      does_not_occur context n nn so &&
-       strictly_positive ((Some (name,(C.Decl so)))::context) (n+1) (nn+1) ta
-   | C.Appl ((C.Rel m)::tl) when m > n && m <= nn ->
-      List.fold_right (fun x i -> i && does_not_occur context n nn x) tl true
-   | C.Appl ((C.MutInd (uri,i,exp_named_subst))::tl) -> 
-      let (ok,paramsno,ity,cl,name) =
-       match CicEnvironment.get_obj uri with
-           C.InductiveDefinition (tl,_,paramsno) ->
-            let (name,_,ity,cl) = List.nth tl i in
-             (List.length tl = 1, paramsno, ity, cl, name)
-         | _ ->
-           raise
-            (TypeCheckerFailure
-              (WrongUriToMutualInductiveDefinitions(U.string_of_uri uri)))
-      in
-       let (params,arguments) = split tl paramsno in
-       let lifted_params = List.map (CicSubstitution.lift 1) params in
-       let cl' =
-        List.map
-         (fun (_,te) ->
-           instantiate_parameters lifted_params
-            (CicSubstitution.subst_vars exp_named_subst te)
-         ) cl
-       in
-        ok &&
-         List.fold_right
-          (fun x i -> i && does_not_occur context n nn x)
-          arguments true &&
-         (*CSC: MEGAPATCH3 (sara' quella giusta?)*)
-         List.fold_right
-          (fun x i ->
-            i &&
-             weakly_positive
-              ((Some (C.Name name,(Cic.Decl ity)))::context) (n+1) (nn+1) uri x
-          ) cl' true
-   | t -> does_not_occur context n nn t
-
-(*CSC l'indice x dei tipi induttivi e' t.c. n < x <= nn *)
-and are_all_occurrences_positive context uri indparamsno i n nn te =
- let module C = Cic in
-  match CicReduction.whd context te with
-     C.Appl ((C.Rel m)::tl) when m = i ->
-      (*CSC: riscrivere fermandosi a 0 *)
-      (* let's check if the inductive type is applied at least to *)
-      (* indparamsno parameters                                   *)
-      let last =
-       List.fold_left
-        (fun k x ->
-          if k = 0 then 0
-          else
-           match CicReduction.whd context x with
-              C.Rel m when m = n - (indparamsno - k) -> k - 1
-            | _ ->
-              raise
-               (TypeCheckerFailure
-                 (WrongRequiredArgument (UriManager.string_of_uri uri)))
-        ) indparamsno tl
-      in
-       if last = 0 then
-        List.fold_right (fun x i -> i && does_not_occur context n nn x) tl true
-       else
-        raise
-         (TypeCheckerFailure
-          (WrongRequiredArgument (UriManager.string_of_uri uri)))
-   | C.Rel m when m = i ->
-      if indparamsno = 0 then
-       true
-      else
-       raise
-        (TypeCheckerFailure
-          (WrongRequiredArgument (UriManager.string_of_uri uri)))
-   | C.Prod (C.Anonymous,source,dest) ->
-      strictly_positive context n nn source &&
-       are_all_occurrences_positive
-        ((Some (C.Anonymous,(C.Decl source)))::context) uri indparamsno
-        (i+1) (n + 1) (nn + 1) dest
-   | C.Prod (name,source,dest) when
-      does_not_occur ((Some (name,(C.Decl source)))::context) 0 n dest ->
-      (* dummy abstraction, so we behave as in the anonimous case *)
-      strictly_positive context n nn source &&
-       are_all_occurrences_positive
-        ((Some (name,(C.Decl source)))::context) uri indparamsno
-        (i+1) (n + 1) (nn + 1) dest
-   | C.Prod (name,source,dest) ->
-      does_not_occur context n nn source &&
-       are_all_occurrences_positive ((Some (name,(C.Decl source)))::context)
-        uri indparamsno (i+1) (n + 1) (nn + 1) dest
-   | _ ->
-     raise
-      (TypeCheckerFailure
-       (NotWellFormedTypeOfInductiveConstructor (UriManager.string_of_uri uri)))
-
-(* Main function to checks the correctness of a mutual *)
-(* inductive block definition. This is the function    *)
-(* exported to the proof-engine.                       *)
-and typecheck_mutual_inductive_defs uri (itl,_,indparamsno) =
- let module U = UriManager in
-  (* let's check if the arity of the inductive types are well *)
-  (* formed                                                   *)
-  List.iter (fun (_,_,x,_) -> let _ = type_of x in ()) itl ;
-
-  (* let's check if the types of the inductive constructors  *)
-  (* are well formed.                                        *)
-  (* In order not to use type_of_aux we put the types of the *)
-  (* mutual inductive types at the head of the types of the  *)
-  (* constructors using Prods                                *)
-  let len = List.length itl in
-   let tys =
-    List.map (fun (n,_,ty,_) -> Some (Cic.Name n,(Cic.Decl ty))) itl in
-   let _ =
-    List.fold_right
-     (fun (_,_,_,cl) i ->
-       List.iter
-        (fun (name,te) -> 
-          let debrujinedte = debrujin_constructor uri len te in
-          let augmented_term =
-           List.fold_right
-            (fun (name,_,ty,_) i -> Cic.Prod (Cic.Name name, ty, i))
-            itl debrujinedte
-          in
-           let _ = type_of augmented_term in
-            (* let's check also the positivity conditions *)
-            if
-             not
-              (are_all_occurrences_positive tys uri indparamsno i 0 len
-                debrujinedte)
-            then
-             raise
-              (TypeCheckerFailure
-                (NotPositiveOccurrences (U.string_of_uri uri)))
-        ) cl ;
-       (i + 1)
-    ) itl 1
-   in
-    ()
-
-(* Main function to checks the correctness of a mutual *)
-(* inductive block definition.                         *)
-and check_mutual_inductive_defs uri =
- function
-    Cic.InductiveDefinition (itl, params, indparamsno) ->
-     typecheck_mutual_inductive_defs uri (itl,params,indparamsno)
-  | _ ->
-    raise
-     (TypeCheckerFailure
-       (WrongUriToMutualInductiveDefinitions (UriManager.string_of_uri uri)))
-
-and type_of_mutual_inductive_defs uri i =
- let module C = Cic in
- let module R = CicReduction in
- let module U = UriManager in
-  let cobj =
-   match CicEnvironment.is_type_checked ~trust:true uri with
-      CicEnvironment.CheckedObj cobj -> cobj
-    | CicEnvironment.UncheckedObj uobj ->
-       Logger.log (`Start_type_checking uri) ;
-       check_mutual_inductive_defs uri uobj ;
-       CicEnvironment.set_type_checking_info uri ;
-       Logger.log (`Type_checking_completed uri) ;
-       (match CicEnvironment.is_type_checked ~trust:false uri with
-          CicEnvironment.CheckedObj cobj -> cobj
-        | CicEnvironment.UncheckedObj _ -> raise CicEnvironmentError
-       )
-  in
-   match cobj with
-      C.InductiveDefinition (dl,_,_) ->
-       let (_,_,arity,_) = List.nth dl i in
-        arity
-    | _ ->
-      raise
-       (TypeCheckerFailure
-         (WrongUriToMutualInductiveDefinitions (U.string_of_uri uri)))
-
-and type_of_mutual_inductive_constr uri i j =
- let module C = Cic in
- let module R = CicReduction in
- let module U = UriManager in
-  let cobj =
-   match CicEnvironment.is_type_checked ~trust:true uri with
-      CicEnvironment.CheckedObj cobj -> cobj
-    | CicEnvironment.UncheckedObj uobj ->
-       Logger.log (`Start_type_checking uri) ;
-       check_mutual_inductive_defs uri uobj ;
-       CicEnvironment.set_type_checking_info uri ;
-       Logger.log (`Type_checking_completed uri) ;
-       (match CicEnvironment.is_type_checked ~trust:false uri with
-          CicEnvironment.CheckedObj cobj -> cobj
-        | CicEnvironment.UncheckedObj _ -> raise CicEnvironmentError
-       )
-  in
-   match cobj with
-      C.InductiveDefinition (dl,_,_) ->
-       let (_,_,_,cl) = List.nth dl i in
-        let (_,ty) = List.nth cl (j-1) in
-         ty
-    | _ ->
-      raise
-       (TypeCheckerFailure
-         (WrongUriToMutualInductiveDefinitions (U.string_of_uri uri)))
-
-and recursive_args context n nn te =
- let module C = Cic in
-  match CicReduction.whd context te with
-     C.Rel _ -> []
-   | C.Var _
-   | C.Meta _
-   | C.Sort _
-   | C.Implicit
-   | C.Cast _ (*CSC ??? *) ->
-      raise (TypeCheckerFailure (Impossible 3)) (* due to type-checking *)
-   | C.Prod (name,so,de) ->
-      (not (does_not_occur context n nn so)) ::
-       (recursive_args ((Some (name,(C.Decl so)))::context) (n+1) (nn + 1) de)
-   | C.Lambda _
-   | C.LetIn _ ->
-      raise (TypeCheckerFailure (Impossible 4)) (* due to type-checking *)
-   | C.Appl _ -> []
-   | C.Const _ -> raise (TypeCheckerFailure (Impossible 5))
-   | C.MutInd _
-   | C.MutConstruct _
-   | C.MutCase _
-   | C.Fix _
-   | C.CoFix _ ->
-      raise (TypeCheckerFailure (Impossible 6)) (* due to type-checking *)
-
-and get_new_safes context p c rl safes n nn x =
- let module C = Cic in
- let module U = UriManager in
- let module R = CicReduction in
-  match (R.whd context c, R.whd context p, rl) with
-     (C.Prod (_,so,ta1), C.Lambda (name,_,ta2), b::tl) ->
-       (* we are sure that the two sources are convertible because we *)
-       (* have just checked this. So let's go along ...               *)
-       let safes' =
-        List.map (fun x -> x + 1) safes
-       in
-        let safes'' =
-         if b then 1::safes' else safes'
-        in
-         get_new_safes ((Some (name,(C.Decl so)))::context)
-          ta2 ta1 tl safes'' (n+1) (nn+1) (x+1)
-   | (C.Prod _, (C.MutConstruct _ as e), _)
-   | (C.Prod _, (C.Rel _ as e), _)
-   | (C.MutInd _, e, [])
-   | (C.Appl _, e, []) -> (e,safes,n,nn,x,context)
-   | (_,_,_) ->
-      (* CSC: If the next exception is raised, it just means that   *)
-      (* CSC: the proof-assistant allows to use very strange things *)
-      (* CSC: as a branch of a case whose type is a Prod. In        *)
-      (* CSC: particular, this means that a new (C.Prod, x,_) case  *)
-      (* CSC: must be considered in this match. (e.g. x = MutCase)  *)
-      raise (TypeCheckerFailure (Impossible 7))
-
-and split_prods context n te =
- let module C = Cic in
- let module R = CicReduction in
-  match (n, R.whd context te) with
-     (0, _) -> context,te
-   | (n, C.Prod (name,so,ta)) when n > 0 ->
-       split_prods ((Some (name,(C.Decl so)))::context) (n - 1) ta
-   | (_, _) -> raise (TypeCheckerFailure (Impossible 8))
-
-and eat_lambdas context n te =
- let module C = Cic in
- let module R = CicReduction in
-  match (n, R.whd context te) with
-     (0, _) -> (te, 0, context)
-   | (n, C.Lambda (name,so,ta)) when n > 0 ->
-      let (te, k, context') =
-       eat_lambdas ((Some (name,(C.Decl so)))::context) (n - 1) ta
-      in
-       (te, k + 1, context')
-   | (_, _) -> raise (TypeCheckerFailure (Impossible 9))
-
-(*CSC: Tutto quello che segue e' l'intuzione di luca ;-) *)
-and check_is_really_smaller_arg context n nn kl x safes te =
- (*CSC: forse la whd si puo' fare solo quando serve veramente. *)
- (*CSC: cfr guarded_by_destructors                             *)
- let module C = Cic in
- let module U = UriManager in
- match CicReduction.whd context te with
-     C.Rel m when List.mem m safes -> true
-   | C.Rel _ -> false
-   | C.Var _
-   | C.Meta _
-   | C.Sort _
-   | C.Implicit 
-   | C.Cast _
-(*   | C.Cast (te,ty) ->
-      check_is_really_smaller_arg n nn kl x safes te &&
-       check_is_really_smaller_arg n nn kl x safes ty*)
-(*   | C.Prod (_,so,ta) ->
-      check_is_really_smaller_arg n nn kl x safes so &&
-       check_is_really_smaller_arg (n+1) (nn+1) kl (x+1)
-        (List.map (fun x -> x + 1) safes) ta*)
-   | C.Prod _ -> raise (TypeCheckerFailure (Impossible 10))
-   | C.Lambda (name,so,ta) ->
-      check_is_really_smaller_arg context n nn kl x safes so &&
-       check_is_really_smaller_arg ((Some (name,(C.Decl so)))::context)
-        (n+1) (nn+1) kl (x+1) (List.map (fun x -> x + 1) safes) ta
-   | C.LetIn (name,so,ta) ->
-      check_is_really_smaller_arg context n nn kl x safes so &&
-       check_is_really_smaller_arg ((Some (name,(C.Def so)))::context)
-        (n+1) (nn+1) kl (x+1) (List.map (fun x -> x + 1) safes) ta
-   | C.Appl (he::_) ->
-      (*CSC: sulla coda ci vogliono dei controlli? secondo noi no, ma *)
-      (*CSC: solo perche' non abbiamo trovato controesempi            *)
-      check_is_really_smaller_arg context n nn kl x safes he
-   | C.Appl [] -> raise (TypeCheckerFailure (Impossible 11))
-   | C.Const _
-   | C.MutInd _ -> raise (TypeCheckerFailure (Impossible 12))
-   | C.MutConstruct _ -> false
-   | C.MutCase (uri,i,outtype,term,pl) ->
-      (match term with
-          C.Rel m when List.mem m safes || m = x ->
-           let (tys,len,isinductive,paramsno,cl) =
-            match CicEnvironment.get_obj uri with
-               C.InductiveDefinition (tl,_,paramsno) ->
-                let tys =
-                 List.map (fun (n,_,ty,_) -> Some (Cic.Name n,(Cic.Decl ty))) tl
-                in
-                 let (_,isinductive,_,cl) = List.nth tl i in
-                  let cl' =
-                   List.map
-                    (fun (id,ty) ->
-                      (id, snd (split_prods tys paramsno ty))) cl
-                  in
-                   (tys,List.length tl,isinductive,paramsno,cl')
-             | _ ->
-               raise
-                (TypeCheckerFailure
-                 (WrongUriToMutualInductiveDefinitions(U.string_of_uri uri)))
-           in
-            if not isinductive then
-              List.fold_right
-               (fun p i ->
-                 i && check_is_really_smaller_arg context n nn kl x safes p)
-               pl true
-            else
-              List.fold_right
-               (fun (p,(_,c)) i ->
-                 let rl' =
-                  let debrujinedte = debrujin_constructor uri len c in
-                   recursive_args tys 0 len debrujinedte
-                 in
-                  let (e,safes',n',nn',x',context') =
-                   get_new_safes context p c rl' safes n nn x
-                  in
-                   i &&
-                   check_is_really_smaller_arg context' n' nn' kl x' safes' e
-               ) (List.combine pl cl) true
-        | C.Appl ((C.Rel m)::tl) when List.mem m safes || m = x ->
-           let (tys,len,isinductive,paramsno,cl) =
-            match CicEnvironment.get_obj uri with
-               C.InductiveDefinition (tl,_,paramsno) ->
-                let (_,isinductive,_,cl) = List.nth tl i in
-                 let tys =
-                  List.map (fun (n,_,ty,_) -> Some(Cic.Name n,(Cic.Decl ty))) tl
-                 in
-                  let cl' =
-                   List.map
-                    (fun (id,ty) ->
-                      (id, snd (split_prods tys paramsno ty))) cl
-                  in
-                   (tys,List.length tl,isinductive,paramsno,cl')
-             | _ ->
-               raise
-                (TypeCheckerFailure
-                  (WrongUriToMutualInductiveDefinitions(U.string_of_uri uri)))
-           in
-            if not isinductive then
-              List.fold_right
-               (fun p i ->
-                 i && check_is_really_smaller_arg context n nn kl x safes p)
-               pl true
-            else
-              (*CSC: supponiamo come prima che nessun controllo sia necessario*)
-              (*CSC: sugli argomenti di una applicazione                      *)
-              List.fold_right
-               (fun (p,(_,c)) i ->
-                 let rl' =
-                  let debrujinedte = debrujin_constructor uri len c in
-                   recursive_args tys 0 len debrujinedte
-                 in
-                  let (e, safes',n',nn',x',context') =
-                   get_new_safes context p c rl' safes n nn x
-                  in
-                   i &&
-                   check_is_really_smaller_arg context' n' nn' kl x' safes' e
-               ) (List.combine pl cl) true
-        | _ ->
-          List.fold_right
-           (fun p i ->
-             i && check_is_really_smaller_arg context n nn kl x safes p
-           ) pl true
-      )
-   | C.Fix (_, fl) ->
-      let len = List.length fl in
-       let n_plus_len = n + len
-       and nn_plus_len = nn + len
-       and x_plus_len = x + len
-       and tys = List.map (fun (n,_,ty,_) -> Some (C.Name n,(C.Decl ty))) fl
-       and safes' = List.map (fun x -> x + len) safes in
-        List.fold_right
-         (fun (_,_,ty,bo) i ->
-           i &&
-            check_is_really_smaller_arg (tys@context) n_plus_len nn_plus_len kl
-             x_plus_len safes' bo
-         ) fl true
-   | C.CoFix (_, fl) ->
-      let len = List.length fl in
-       let n_plus_len = n + len
-       and nn_plus_len = nn + len
-       and x_plus_len = x + len
-       and tys = List.map (fun (n,ty,_) -> Some (C.Name n,(C.Decl ty))) fl
-       and safes' = List.map (fun x -> x + len) safes in
-        List.fold_right
-         (fun (_,ty,bo) i ->
-           i &&
-            check_is_really_smaller_arg (tys@context) n_plus_len nn_plus_len kl
-             x_plus_len safes' bo
-         ) fl true
-
-and guarded_by_destructors context n nn kl x safes =
- let module C = Cic in
- let module U = UriManager in
-  function
-     C.Rel m when m > n && m <= nn -> false
-   | C.Rel n ->
-      (match List.nth context (n-1) with
-          Some (_,C.Decl _) -> true
-        | Some (_,C.Def bo) -> guarded_by_destructors context n nn kl x safes bo
-       | None -> raise (TypeCheckerFailure RelToHiddenHypothesis)
-      )
-   | C.Meta _
-   | C.Sort _
-   | C.Implicit -> true
-   | C.Cast (te,ty) ->
-      guarded_by_destructors context n nn kl x safes te &&
-       guarded_by_destructors context n nn kl x safes ty
-   | C.Prod (name,so,ta) ->
-      guarded_by_destructors context n nn kl x safes so &&
-       guarded_by_destructors ((Some (name,(C.Decl so)))::context)
-        (n+1) (nn+1) kl (x+1) (List.map (fun x -> x + 1) safes) ta
-   | C.Lambda (name,so,ta) ->
-      guarded_by_destructors context n nn kl x safes so &&
-       guarded_by_destructors ((Some (name,(C.Decl so)))::context)
-        (n+1) (nn+1) kl (x+1) (List.map (fun x -> x + 1) safes) ta
-   | C.LetIn (name,so,ta) ->
-      guarded_by_destructors context n nn kl x safes so &&
-       guarded_by_destructors ((Some (name,(C.Def so)))::context)
-        (n+1) (nn+1) kl (x+1) (List.map (fun x -> x + 1) safes) ta
-   | C.Appl ((C.Rel m)::tl) when m > n && m <= nn ->
-      let k = List.nth kl (m - n - 1) in
-       if not (List.length tl > k) then false
-       else
-        List.fold_right
-         (fun param i ->
-           i && guarded_by_destructors context n nn kl x safes param
-         ) tl true &&
-         check_is_really_smaller_arg context n nn kl x safes (List.nth tl k)
-   | C.Appl tl ->
-      List.fold_right
-       (fun t i -> i && guarded_by_destructors context n nn kl x safes t)
-       tl true
-   | C.Var (_,exp_named_subst)
-   | C.Const (_,exp_named_subst)
-   | C.MutInd (_,_,exp_named_subst)
-   | C.MutConstruct (_,_,_,exp_named_subst) ->
-      List.fold_right
-       (fun (_,t) i -> i && guarded_by_destructors context n nn kl x safes t)
-       exp_named_subst true
-   | C.MutCase (uri,i,outtype,term,pl) ->
-      (match term with
-          C.Rel m when List.mem m safes || m = x ->
-           let (tys,len,isinductive,paramsno,cl) =
-            match CicEnvironment.get_obj uri with
-               C.InductiveDefinition (tl,_,paramsno) ->
-                let (_,isinductive,_,cl) = List.nth tl i in
-                 let tys =
-                  List.map (fun (n,_,ty,_) -> Some(Cic.Name n,(Cic.Decl ty))) tl
-                 in
-                  let cl' =
-                   List.map
-                    (fun (id,ty) ->
-                      (id, snd (split_prods tys paramsno ty))) cl
-                  in
-                   (tys,List.length tl,isinductive,paramsno,cl')
-             | _ ->
-               raise
-                (TypeCheckerFailure
-                  (WrongUriToMutualInductiveDefinitions(U.string_of_uri uri)))
-           in
-            if not isinductive then
-             guarded_by_destructors context n nn kl x safes outtype &&
-              guarded_by_destructors context n nn kl x safes term &&
-              (*CSC: manca ??? il controllo sul tipo di term? *)
-              List.fold_right
-               (fun p i ->
-                 i && guarded_by_destructors context n nn kl x safes p)
-               pl true
-            else
-             guarded_by_destructors context n nn kl x safes outtype &&
-              (*CSC: manca ??? il controllo sul tipo di term? *)
-              List.fold_right
-               (fun (p,(_,c)) i ->
-                 let rl' =
-                  let debrujinedte = debrujin_constructor uri len c in
-                   recursive_args tys 0 len debrujinedte
-                 in
-                  let (e,safes',n',nn',x',context') =
-                   get_new_safes context p c rl' safes n nn x
-                  in
-                   i &&
-                   guarded_by_destructors context' n' nn' kl x' safes' e
-               ) (List.combine pl cl) true
-        | C.Appl ((C.Rel m)::tl) when List.mem m safes || m = x ->
-           let (tys,len,isinductive,paramsno,cl) =
-            match CicEnvironment.get_obj uri with
-               C.InductiveDefinition (tl,_,paramsno) ->
-                let (_,isinductive,_,cl) = List.nth tl i in
-                 let tys =
-                  List.map (fun (n,_,ty,_) -> Some(Cic.Name n,(Cic.Decl ty))) tl
-                 in
-                  let cl' =
-                   List.map
-                    (fun (id,ty) ->
-                      (id, snd (split_prods tys paramsno ty))) cl
-                  in
-                   (tys,List.length tl,isinductive,paramsno,cl')
-             | _ ->
-               raise
-                (TypeCheckerFailure
-                  (WrongUriToMutualInductiveDefinitions(U.string_of_uri uri)))
-           in
-            if not isinductive then
-             guarded_by_destructors context n nn kl x safes outtype &&
-              guarded_by_destructors context n nn kl x safes term &&
-              (*CSC: manca ??? il controllo sul tipo di term? *)
-              List.fold_right
-               (fun p i ->
-                 i && guarded_by_destructors context n nn kl x safes p)
-               pl true
-            else
-             guarded_by_destructors context n nn kl x safes outtype &&
-              (*CSC: manca ??? il controllo sul tipo di term? *)
-              List.fold_right
-               (fun t i ->
-                 i && guarded_by_destructors context n nn kl x safes t)
-               tl true &&
-              List.fold_right
-               (fun (p,(_,c)) i ->
-                 let rl' =
-                  let debrujinedte = debrujin_constructor uri len c in
-                   recursive_args tys 0 len debrujinedte
-                 in
-                  let (e, safes',n',nn',x',context') =
-                   get_new_safes context p c rl' safes n nn x
-                  in
-                   i &&
-                   guarded_by_destructors context' n' nn' kl x' safes' e
-               ) (List.combine pl cl) true
-        | _ ->
-          guarded_by_destructors context n nn kl x safes outtype &&
-           guarded_by_destructors context n nn kl x safes term &&
-           (*CSC: manca ??? il controllo sul tipo di term? *)
-           List.fold_right
-            (fun p i -> i && guarded_by_destructors context n nn kl x safes p)
-            pl true
-      )
-   | C.Fix (_, fl) ->
-      let len = List.length fl in
-       let n_plus_len = n + len
-       and nn_plus_len = nn + len
-       and x_plus_len = x + len
-       and tys = List.map (fun (n,_,ty,_) -> Some (C.Name n,(C.Decl ty))) fl
-       and safes' = List.map (fun x -> x + len) safes in
-        List.fold_right
-         (fun (_,_,ty,bo) i ->
-           i && guarded_by_destructors context n nn kl x_plus_len safes' ty &&
-            guarded_by_destructors (tys@context) n_plus_len nn_plus_len kl
-             x_plus_len safes' bo
-         ) fl true
-   | C.CoFix (_, fl) ->
-      let len = List.length fl in
-       let n_plus_len = n + len
-       and nn_plus_len = nn + len
-       and x_plus_len = x + len
-       and tys = List.map (fun (n,ty,_) -> Some (C.Name n,(C.Decl ty))) fl
-       and safes' = List.map (fun x -> x + len) safes in
-        List.fold_right
-         (fun (_,ty,bo) i ->
-           i &&
-            guarded_by_destructors context n nn kl x_plus_len safes' ty &&
-            guarded_by_destructors (tys@context) n_plus_len nn_plus_len kl
-             x_plus_len safes' bo
-         ) fl true
-
-(* the boolean h means already protected *)
-(* args is the list of arguments the type of the constructor that may be *)
-(* found in head position must be applied to.                            *)
-(*CSC: coInductiveTypeURI non cambia mai di ricorsione in ricorsione *)
-and guarded_by_constructors context n nn h te args coInductiveTypeURI =
- let module C = Cic in
-  (*CSC: There is a lot of code replication between the cases X and    *)
-  (*CSC: (C.Appl X tl). Maybe it will be better to define a function   *)
-  (*CSC: that maps X into (C.Appl X []) when X is not already a C.Appl *)
-  match CicReduction.whd context te with
-     C.Rel m when m > n && m <= nn -> h
-   | C.Rel _ -> true
-   | C.Meta _
-   | C.Sort _
-   | C.Implicit
-   | C.Cast _
-   | C.Prod _
-   | C.LetIn _ ->
-      (* the term has just been type-checked *)
-      raise (TypeCheckerFailure (Impossible 17))
-   | C.Lambda (name,so,de) ->
-      does_not_occur context n nn so &&
-       guarded_by_constructors ((Some (name,(C.Decl so)))::context)
-        (n + 1) (nn + 1) h de args coInductiveTypeURI
-   | C.Appl ((C.Rel m)::tl) when m > n && m <= nn ->
-      h &&
-       List.fold_right (fun x i -> i && does_not_occur context n nn x) tl true
-   | C.Appl ((C.MutConstruct (uri,i,j,exp_named_subst))::tl) ->
-      let consty =
-       match CicEnvironment.get_cooked_obj ~trust:false uri with
-          C.InductiveDefinition (itl,_,_) ->
-           let (_,_,_,cl) = List.nth itl i in
-            let (_,cons) = List.nth cl (j - 1) in
-             CicSubstitution.subst_vars exp_named_subst cons
-        | _ ->
-         raise
-          (TypeCheckerFailure
-            (WrongUriToMutualInductiveDefinitions
-              (UriManager.string_of_uri uri)))
-      in
-       let rec analyse_branch context ty te =
-        match CicReduction.whd context ty with
-           C.Meta _ -> raise (TypeCheckerFailure (Impossible 34))
-         | C.Rel _
-         | C.Var _
-         | C.Sort _ ->
-            does_not_occur context n nn te
-         | C.Implicit
-         | C.Cast _ ->
-            raise (TypeCheckerFailure (Impossible 24))(* due to type-checking *)
-         | C.Prod (name,so,de) ->
-            analyse_branch ((Some (name,(C.Decl so)))::context) de te
-         | C.Lambda _
-         | C.LetIn _ ->
-            raise (TypeCheckerFailure (Impossible 25))(* due to type-checking *)
-         | C.Appl ((C.MutInd (uri,_,_))::_) as ty
-            when uri == coInductiveTypeURI -> 
-             guarded_by_constructors context n nn true te [] coInductiveTypeURI
-         | C.Appl ((C.MutInd (uri,_,_))::_) as ty -> 
-            guarded_by_constructors context n nn true te tl coInductiveTypeURI
-         | C.Appl _ ->
-            does_not_occur context n nn te
-         | C.Const _ -> raise (TypeCheckerFailure (Impossible 26))
-         | C.MutInd (uri,_,_) when uri == coInductiveTypeURI ->
-            guarded_by_constructors context n nn true te [] coInductiveTypeURI
-         | C.MutInd _ ->
-            does_not_occur context n nn te
-         | C.MutConstruct _ -> raise (TypeCheckerFailure (Impossible 27))
-         (*CSC: we do not consider backbones with a MutCase, Fix, Cofix *)
-         (*CSC: in head position.                                       *)
-         | C.MutCase _
-         | C.Fix _
-         | C.CoFix _ ->
-            raise (TypeCheckerFailure (Impossible 28))(* due to type-checking *)
-       in
-       let rec analyse_instantiated_type context ty l =
-        match CicReduction.whd context ty with
-           C.Rel _
-         | C.Var _
-         | C.Meta _
-         | C.Sort _
-         | C.Implicit
-         | C.Cast _ ->
-            raise (TypeCheckerFailure (Impossible 29))(* due to type-checking *)
-         | C.Prod (name,so,de) ->
-            begin
-             match l with
-                [] -> true
-              | he::tl ->
-                 analyse_branch context so he &&
-                  analyse_instantiated_type ((Some (name,(C.Decl so)))::context)
-                   de tl
-            end
-         | C.Lambda _
-         | C.LetIn _ ->
-            raise (TypeCheckerFailure (Impossible 30))(* due to type-checking *)
-         | C.Appl _ -> 
-            List.fold_left
-             (fun i x -> i && does_not_occur context n nn x) true l
-         | C.Const _ -> raise (TypeCheckerFailure (Impossible 31))
-         | C.MutInd _ ->
-            List.fold_left
-             (fun i x -> i && does_not_occur context n nn x) true l
-         | C.MutConstruct _ -> raise (TypeCheckerFailure (Impossible 32))
-         (*CSC: we do not consider backbones with a MutCase, Fix, Cofix *)
-         (*CSC: in head position.                                       *)
-         | C.MutCase _
-         | C.Fix _
-         | C.CoFix _ ->
-            raise (TypeCheckerFailure (Impossible 33))(* due to type-checking *)
-       in
-        let rec instantiate_type args consty =
-         function
-            [] -> true
-          | tlhe::tltl as l ->
-             let consty' = CicReduction.whd context consty in
-              match args with 
-                 he::tl ->
-                  begin
-                   match consty' with
-                      C.Prod (_,_,de) ->
-                       let instantiated_de = CicSubstitution.subst he de in
-                        (*CSC: siamo sicuri che non sia troppo forte? *)
-                        does_not_occur context n nn tlhe &
-                         instantiate_type tl instantiated_de tltl
-                    | _ ->
-                      (*CSC:We do not consider backbones with a MutCase, a    *)
-                      (*CSC:FixPoint, a CoFixPoint and so on in head position.*)
-                      raise (TypeCheckerFailure (Impossible 23))
-                  end
-               | [] -> analyse_instantiated_type context consty' l
-                  (* These are all the other cases *)
-       in
-        instantiate_type args consty tl
-   | C.Appl ((C.CoFix (_,fl))::tl) ->
-      List.fold_left (fun i x -> i && does_not_occur context n nn x) true tl &&
-       let len = List.length fl in
-        let n_plus_len = n + len
-        and nn_plus_len = nn + len
-        (*CSC: Is a Decl of the ty ok or should I use Def of a Fix? *)
-        and tys = List.map (fun (n,ty,_) -> Some (C.Name n,(C.Decl ty))) fl in
-         List.fold_right
-          (fun (_,ty,bo) i ->
-            i && does_not_occur context n nn ty &&
-             guarded_by_constructors (tys@context) n_plus_len nn_plus_len h bo
-              args coInductiveTypeURI
-          ) fl true
-   | C.Appl ((C.MutCase (_,_,out,te,pl))::tl) ->
-       List.fold_left (fun i x -> i && does_not_occur context n nn x) true tl &&
-        does_not_occur context n nn out &&
-         does_not_occur context n nn te &&
-          List.fold_right
-           (fun x i ->
-             i &&
-             guarded_by_constructors context n nn h x args coInductiveTypeURI
-           ) pl true
-   | C.Appl l ->
-      List.fold_right (fun x i -> i && does_not_occur context n nn x) l true
-   | C.Var (_,exp_named_subst)
-   | C.Const (_,exp_named_subst) ->
-      List.fold_right
-       (fun (_,x) i -> i && does_not_occur context n nn x) exp_named_subst true
-   | C.MutInd _ -> assert false
-   | C.MutConstruct (_,_,_,exp_named_subst) ->
-      List.fold_right
-       (fun (_,x) i -> i && does_not_occur context n nn x) exp_named_subst true
-   | C.MutCase (_,_,out,te,pl) ->
-       does_not_occur context n nn out &&
-        does_not_occur context n nn te &&
-         List.fold_right
-          (fun x i ->
-            i &&
-             guarded_by_constructors context n nn h x args coInductiveTypeURI
-          ) pl true
-   | C.Fix (_,fl) ->
-      let len = List.length fl in
-       let n_plus_len = n + len
-       and nn_plus_len = nn + len
-       (*CSC: Is a Decl of the ty ok or should I use Def of a Fix? *)
-       and tys = List.map (fun (n,_,ty,_) -> Some (C.Name n,(C.Decl ty))) fl in
-        List.fold_right
-         (fun (_,_,ty,bo) i ->
-           i && does_not_occur context n nn ty &&
-            does_not_occur (tys@context) n_plus_len nn_plus_len bo
-         ) fl true
-   | C.CoFix (_,fl) ->
-      let len = List.length fl in
-       let n_plus_len = n + len
-       and nn_plus_len = nn + len
-       (*CSC: Is a Decl of the ty ok or should I use Def of a Fix? *)
-       and tys = List.map (fun (n,ty,_) -> Some (C.Name n,(C.Decl ty))) fl in
-        List.fold_right
-         (fun (_,ty,bo) i ->
-           i && does_not_occur context n nn ty &&
-            guarded_by_constructors (tys@context) n_plus_len nn_plus_len h bo
-             args coInductiveTypeURI
-         ) fl true
-
-and check_allowed_sort_elimination context uri i need_dummy ind arity1 arity2 =
- let module C = Cic in
- let module U = UriManager in
-  match (CicReduction.whd context arity1, CicReduction.whd context arity2) with
-     (C.Prod (_,so1,de1), C.Prod (_,so2,de2))
-      when CicReduction.are_convertible context so1 so2 ->
-       check_allowed_sort_elimination context uri i need_dummy
-        (C.Appl [CicSubstitution.lift 1 ind ; C.Rel 1]) de1 de2
-   | (C.Sort C.Prop, C.Sort C.Prop) when need_dummy -> true
-   | (C.Sort C.Prop, C.Sort C.Set)
-   | (C.Sort C.Prop, C.Sort C.Type) when need_dummy ->
-(*CSC: WRONG. MISSING CONDITIONS ON THE ARGUMENTS OF THE CONSTRUTOR *)
-       (match CicEnvironment.get_obj uri with
-           C.InductiveDefinition (itl,_,_) ->
-            let (_,_,_,cl) = List.nth itl i in
-             (* is a singleton definition or the empty proposition? *)
-             List.length cl = 1 || List.length cl = 0
-         | _ ->
-           raise
-            (TypeCheckerFailure
-              (WrongUriToMutualInductiveDefinitions (U.string_of_uri uri)))
-       )
-   | (C.Sort C.Set, C.Sort C.Prop) when need_dummy -> true
-   | (C.Sort C.Set, C.Sort C.Set) when need_dummy -> true
-   | (C.Sort C.Set, C.Sort C.Type) when need_dummy ->
-       (match CicEnvironment.get_obj uri with
-           C.InductiveDefinition (itl,_,paramsno) ->
-            let tys =
-             List.map (fun (n,_,ty,_) -> Some (Cic.Name n,(Cic.Decl ty))) itl
-            in
-             let (_,_,_,cl) = List.nth itl i in
-              List.fold_right
-               (fun (_,x) i -> i && is_small tys paramsno x) cl true
-         | _ ->
-           raise
-            (TypeCheckerFailure
-              (WrongUriToMutualInductiveDefinitions (U.string_of_uri uri)))
-       )
-   | (C.Sort C.Type, C.Sort _) when need_dummy -> true
-   | (C.Sort C.Prop, C.Prod (name,so,ta)) when not need_dummy ->
-       let res = CicReduction.are_convertible context so ind
-       in
-        res &&
-        (match CicReduction.whd ((Some (name,(C.Decl so)))::context) ta with
-            C.Sort C.Prop -> true
-          | C.Sort C.Set ->
-             (match CicEnvironment.get_obj uri with
-                 C.InductiveDefinition (itl,_,_) ->
-                  let (_,_,_,cl) = List.nth itl i in
-                   (* is a singleton definition? *)
-                   List.length cl = 1
-               | _ ->
-                 raise
-                  (TypeCheckerFailure
-                    (WrongUriToMutualInductiveDefinitions(U.string_of_uri uri)))
-             )
-          | _ -> false
-        )
-   | (C.Sort C.Set, C.Prod (name,so,ta)) when not need_dummy ->
-       let res = CicReduction.are_convertible context so ind
-       in
-        res &&
-        (match CicReduction.whd ((Some (name,(C.Decl so)))::context) ta with
-            C.Sort C.Prop
-          | C.Sort C.Set  -> true
-          | C.Sort C.Type ->
-             (match CicEnvironment.get_obj uri with
-                 C.InductiveDefinition (itl,_,paramsno) ->
-                  let (_,_,_,cl) = List.nth itl i in
-                   let tys =
-                    List.map
-                     (fun (n,_,ty,_) -> Some (Cic.Name n,(Cic.Decl ty))) itl
-                   in
-                    List.fold_right
-                     (fun (_,x) i -> i && is_small tys paramsno x) cl true
-               | _ ->
-                 raise
-                  (TypeCheckerFailure
-                    (WrongUriToMutualInductiveDefinitions(U.string_of_uri uri)))
-             )
-          | _ -> raise (TypeCheckerFailure (Impossible 19))
-        )
-   | (C.Sort C.Type, C.Prod (_,so,_)) when not need_dummy ->
-       CicReduction.are_convertible context so ind
-   | (_,_) -> false
-  
-and type_of_branch context argsno need_dummy outtype term constype =
- let module C = Cic in
- let module R = CicReduction in
-  match R.whd context constype with
-     C.MutInd (_,_,_) ->
-      if need_dummy then
-       outtype
-      else
-       C.Appl [outtype ; term]
-   | C.Appl (C.MutInd (_,_,_)::tl) ->
-      let (_,arguments) = split tl argsno
-      in
-       if need_dummy && arguments = [] then
-        outtype
-       else
-        C.Appl (outtype::arguments@(if need_dummy then [] else [term]))
-   | C.Prod (name,so,de) ->
-      let term' =
-       match CicSubstitution.lift 1 term with
-          C.Appl l -> C.Appl (l@[C.Rel 1])
-        | t -> C.Appl [t ; C.Rel 1]
-      in
-       C.Prod (C.Anonymous,so,type_of_branch
-        ((Some (name,(C.Decl so)))::context) argsno need_dummy
-        (CicSubstitution.lift 1 outtype) term' de)
-  | _ -> raise (TypeCheckerFailure (Impossible 20))
-
-(* check_metasenv_consistency checks that the "canonical" context of a
-metavariable is consitent - up to relocation via the relocation list l -
-with the actual context *)
-
-and check_metasenv_consistency metasenv context canonical_context l =
-  let module C = Cic in
-  let module R = CicReduction in
-  let module S = CicSubstitution in
-   let lifted_canonical_context = 
-    let rec aux i =
-     function
-        [] -> []
-      | (Some (n,C.Decl t))::tl ->
-         (Some (n,C.Decl (S.lift_meta l (S.lift i t))))::(aux (i+1) tl)
-      | (Some (n,C.Def t))::tl ->
-         (Some (n,C.Def (S.lift_meta l (S.lift i t))))::(aux (i+1) tl)
-      | None::tl -> None::(aux (i+1) tl)
-    in
-     aux 1 canonical_context
-   in
-    List.iter2 
-     (fun t ct -> 
-       let res =
-        match (t,ct) with
-           _,None -> true
-         | Some t,Some (_,C.Def ct) ->
-            R.are_convertible context t ct
-         | Some t,Some (_,C.Decl ct) ->
-            R.are_convertible context (type_of_aux' metasenv context t) ct
-         | _, _  -> false
-       in
-        if not res then raise (TypeCheckerFailure MetasenvInconsistency)
-     ) l lifted_canonical_context 
-
-(* type_of_aux' is just another name (with a different scope) for type_of_aux *)
-and type_of_aux' metasenv context t =
- let rec type_of_aux context =
-  let module C = Cic in
-  let module R = CicReduction in
-  let module S = CicSubstitution in
-  let module U = UriManager in
-   function
-      C.Rel n ->
-       (try
-         match List.nth context (n - 1) with
-            Some (_,C.Decl t) -> S.lift n t
-          | Some (_,C.Def bo) -> type_of_aux context (S.lift n bo)
-         | None -> raise (TypeCheckerFailure RelToHiddenHypothesis)
-        with
-         _ -> raise (TypeCheckerFailure (NotWellTyped "Not a close term"))
-       )
-    | C.Var (uri,exp_named_subst) ->
-      incr fdebug ;
-      check_exp_named_subst context exp_named_subst ;
-      let ty =
-       CicSubstitution.subst_vars exp_named_subst (type_of_variable uri)
-      in
-       decr fdebug ;
-       ty
-    | C.Meta (n,l) -> 
-       let (_,canonical_context,ty) =
-        List.find (function (m,_,_) -> n = m) metasenv
-       in
-        check_metasenv_consistency metasenv context canonical_context l;
-        CicSubstitution.lift_meta l ty
-    | C.Sort s -> C.Sort C.Type (*CSC manca la gestione degli universi!!! *)
-    | C.Implicit -> raise (TypeCheckerFailure (Impossible 21))
-    | C.Cast (te,ty) ->
-       let _ = type_of_aux context ty in
-        if R.are_convertible context (type_of_aux context te) ty then ty
-        else raise (TypeCheckerFailure (NotWellTyped "Cast"))
-    | C.Prod (name,s,t) ->
-       let sort1 = type_of_aux context s
-       and sort2 = type_of_aux ((Some (name,(C.Decl s)))::context) t in
-        sort_of_prod context (name,s) (sort1,sort2)
-   | C.Lambda (n,s,t) ->
-       let sort1 = type_of_aux context s
-       and type2 = type_of_aux ((Some (n,(C.Decl s)))::context) t in
-        let sort2 = type_of_aux ((Some (n,(C.Decl s)))::context) type2 in
-         (* only to check if the product is well-typed *)
-         let _ = sort_of_prod context (n,s) (sort1,sort2) in
-          C.Prod (n,s,type2)
-   | C.LetIn (n,s,t) ->
-      (* only to check if s is well-typed *)
-      let _ = type_of_aux context s in
-       (* The type of a LetIn is a LetIn. Extremely slow since the computed
-          LetIn is later reduced and maybe also re-checked.
-       (C.LetIn (n,s, type_of_aux ((Some (n,(C.Def s)))::context) t))
-       *)
-       (* The type of the LetIn is reduced. Much faster than the previous
-          solution. Moreover the inferred type is probably very different
-          from the expected one.
-       (CicReduction.whd context
-        (C.LetIn (n,s, type_of_aux ((Some (n,(C.Def s)))::context) t)))
-       *)
-       (* One-step LetIn reduction. Even faster than the previous solution.
-          Moreover the inferred type is closer to the expected one. *)
-       (CicSubstitution.subst s
-        (type_of_aux ((Some (n,(C.Def s)))::context) t))
-   | C.Appl (he::tl) when List.length tl > 0 ->
-      let hetype = type_of_aux context he
-      and tlbody_and_type = List.map (fun x -> (x, type_of_aux context x)) tl in
-       eat_prods context hetype tlbody_and_type
-   | C.Appl _ -> raise (TypeCheckerFailure (NotWellTyped "Appl: no arguments"))
-   | C.Const (uri,exp_named_subst) ->
-      incr fdebug ;
-      check_exp_named_subst context exp_named_subst ;
-      let cty =
-       CicSubstitution.subst_vars exp_named_subst (type_of_constant uri)
-      in
-       decr fdebug ;
-       cty
-   | C.MutInd (uri,i,exp_named_subst) ->
-      incr fdebug ;
-      check_exp_named_subst context exp_named_subst ;
-      let cty =
-       CicSubstitution.subst_vars exp_named_subst
-        (type_of_mutual_inductive_defs uri i)
-      in
-       decr fdebug ;
-       cty
-   | C.MutConstruct (uri,i,j,exp_named_subst) ->
-      check_exp_named_subst context exp_named_subst ;
-      let cty =
-       CicSubstitution.subst_vars exp_named_subst
-        (type_of_mutual_inductive_constr uri i j)
-      in
-       cty
-   | C.MutCase (uri,i,outtype,term,pl) ->
-      let outsort = type_of_aux context outtype in
-      let (need_dummy, k) =
-       let rec guess_args context t =
-        match CicReduction.whd context t with
-           C.Sort _ -> (true, 0)
-         | C.Prod (name, s, t) ->
-            let (b, n) = guess_args ((Some (name,(C.Decl s)))::context) t in
-             if n = 0 then
-              (* last prod before sort *)
-              match CicReduction.whd context s with
-(*CSC: for _ see comment below about the missing named_exp_subst ?????????? *)
-                 C.MutInd (uri',i',_) when U.eq uri' uri && i' = i ->
-                  (false, 1)
-(*CSC: for _ see comment below about the missing named_exp_subst ?????????? *)
-               | C.Appl ((C.MutInd (uri',i',_)) :: _)
-                  when U.eq uri' uri && i' = i -> (false, 1)
-               | _ -> (true, 1)
-             else
-              (b, n + 1)
-         | _ ->
-           raise
-            (TypeCheckerFailure (NotWellTyped "MutCase: outtype ill-formed"))
-       in
-        (*CSC whd non serve dopo type_of_aux ? *)
-        let (b, k) = guess_args context outsort in
-         if not b then (b, k - 1) else (b, k)
-      in
-      let (parameters, arguments, exp_named_subst) =
-        match R.whd context (type_of_aux context term) with
-           (*CSC manca il caso dei CAST *)
-(*CSC: ma servono i parametri (uri,i)? Se si', perche' non serve anche il *)
-(*CSC: parametro exp_named_subst? Se no, perche' non li togliamo?         *)
-(*CSC: Hint: nella DTD servono per gli stylesheet.                        *)
-           C.MutInd (uri',i',exp_named_subst) as typ ->
-            if U.eq uri uri' && i = i' then ([],[],exp_named_subst)
-            else raise (TypeCheckerFailure
-             (NotWellTyped ("MutCase: the term is of type " ^
-             CicPp.ppterm typ ^
-             " instead of type " ^ (U.string_of_uri uri) ^ "#1/" ^
-             string_of_int i ^ "{_}")))
-         | C.Appl ((C.MutInd (uri',i',exp_named_subst) as typ):: tl) ->
-            if U.eq uri uri' && i = i' then
-             let params,args =
-              split tl (List.length tl - k)
-             in params,args,exp_named_subst
-            else raise (TypeCheckerFailure (NotWellTyped
-             ("MutCase: the term is of type " ^
-             CicPp.ppterm typ ^
-             " instead of type " ^ (U.string_of_uri uri) ^ "#1/" ^
-             string_of_int i ^ "{_}")))
-         | _ -> raise (TypeCheckerFailure
-                 (NotWellTyped "MutCase: the term is not an inductive one"))
-      in
-       (* let's control if the sort elimination is allowed: [(I q1 ... qr)|B] *)
-       let sort_of_ind_type =
-        if parameters = [] then
-         C.MutInd (uri,i,exp_named_subst)
-        else
-         C.Appl ((C.MutInd (uri,i,exp_named_subst))::parameters)
-       in
-        if not (check_allowed_sort_elimination context uri i need_dummy
-         sort_of_ind_type (type_of_aux context sort_of_ind_type) outsort)
-        then
-         raise
-          (TypeCheckerFailure
-            (NotWellTyped "MutCase: not allowed sort elimination")) ;
-
-        (* let's check if the type of branches are right *)
-        let parsno =
-         match CicEnvironment.get_cooked_obj ~trust:false uri with
-            C.InductiveDefinition (_,_,parsno) -> parsno
-          | _ ->
-            raise
-             (TypeCheckerFailure
-               (WrongUriToMutualInductiveDefinitions (U.string_of_uri uri)))
-        in
-         let (_,branches_ok) =
-          List.fold_left
-           (fun (j,b) p ->
-             let cons =
-              if parameters = [] then
-               (C.MutConstruct (uri,i,j,exp_named_subst))
-              else
-               (C.Appl (C.MutConstruct (uri,i,j,exp_named_subst)::parameters))
-             in
-(*
-              (j + 1, b &&
-*)
-              (j + 1,
-let res = b &&
-               R.are_convertible context (type_of_aux context p)
-                (type_of_branch context parsno need_dummy outtype cons
-                  (type_of_aux context cons))
-in if not res then prerr_endline ("#### " ^ CicPp.ppterm (type_of_aux context p) ^ " <==> " ^ CicPp.ppterm (type_of_branch context parsno need_dummy outtype cons (type_of_aux context cons))) ; res
-              )
-           ) (1,true) pl
-         in
-          if not branches_ok then
-           raise
-            (TypeCheckerFailure
-              (NotWellTyped "MutCase: wrong type of a branch")) ;
-
-          if not need_dummy then
-           C.Appl ((outtype::arguments)@[term])
-          else if arguments = [] then
-           outtype
-          else
-           C.Appl (outtype::arguments)
-   | C.Fix (i,fl) ->
-      let types_times_kl =
-       List.rev
-        (List.map
-          (fun (n,k,ty,_) ->
-            let _ = type_of_aux context ty in
-             (Some (C.Name n,(C.Decl ty)),k)) fl)
-      in
-      let (types,kl) = List.split types_times_kl in
-       let len = List.length types in
-        List.iter
-         (fun (name,x,ty,bo) ->
-           if
-            (R.are_convertible (types@context) (type_of_aux (types@context) bo)
-             (CicSubstitution.lift len ty))
-           then
-            begin
-             let (m, eaten, context') =
-              eat_lambdas (types @ context) (x + 1) bo
-             in
-              (*let's control the guarded by destructors conditions D{f,k,x,M}*)
-              if
-               not
-                (guarded_by_destructors context' eaten (len + eaten) kl 1 [] m)
-              then
-               raise
-                (TypeCheckerFailure
-                  (NotWellTyped "Fix: not guarded by destructors"))
-            end
-           else
-            raise (TypeCheckerFailure (NotWellTyped "Fix: ill-typed bodies"))
-         ) fl ;
-      
-        (*CSC: controlli mancanti solo su D{f,k,x,M} *)
-        let (_,_,ty,_) = List.nth fl i in
-        ty
-   | C.CoFix (i,fl) ->
-      let types =
-       List.rev
-        (List.map
-          (fun (n,ty,_) -> 
-           let _ = type_of_aux context ty in Some (C.Name n,(C.Decl ty))) fl)
-      in
-       let len = List.length types in
-        List.iter
-         (fun (_,ty,bo) ->
-           if
-            (R.are_convertible (types @ context)
-             (type_of_aux (types @ context) bo) (CicSubstitution.lift len ty))
-           then
-            begin
-             (* let's control that the returned type is coinductive *)
-             match returns_a_coinductive context ty with
-                None ->
-                 raise
-                  (TypeCheckerFailure
-                    (NotWellTyped "CoFix: does not return a coinductive type"))
-              | Some uri ->
-                 (*let's control the guarded by constructors conditions C{f,M}*)
-                 if
-                  not
-                   (guarded_by_constructors (types @ context) 0 len false bo
-                     [] uri)
-                 then
-                  raise
-                   (TypeCheckerFailure
-                     (NotWellTyped "CoFix: not guarded by constructors"))
-            end
-           else
-            raise
-             (TypeCheckerFailure
-               (NotWellTyped "CoFix: ill-typed bodies"))
-         ) fl ;
-      
-        let (_,ty,_) = List.nth fl i in
-         ty
-
- and check_exp_named_subst context =
-  let rec check_exp_named_subst_aux substs =
-   function
-      [] -> ()
-    | ((uri,t) as subst)::tl ->
-       let typeofvar =
-        CicSubstitution.subst_vars substs (type_of_variable uri) in
-       (match CicEnvironment.get_cooked_obj ~trust:false uri with
-           Cic.Variable (_,Some bo,_,_) ->
-            raise
-             (TypeCheckerFailure
-               (NotWellTyped
-                 "A variable with a body can not be explicit substituted"))
-         | Cic.Variable (_,None,_,_) -> ()
-         | _ ->
-            raise
-             (TypeCheckerFailure
-               (WrongUriToVariable (UriManager.string_of_uri uri)))
-       ) ;
-       let typeoft = type_of_aux context t in
-        if CicReduction.are_convertible context typeoft typeofvar then
-         check_exp_named_subst_aux (substs@[subst]) tl
-        else
-         begin
-          CicReduction.fdebug := 0 ;
-          ignore (CicReduction.are_convertible context typeoft typeofvar) ;
-          fdebug := 0 ;
-          debug typeoft [typeofvar] ;
-          raise
-           (TypeCheckerFailure
-             (NotWellTyped "Wrong Explicit Named Substitution"))
-         end
-  in
-   check_exp_named_subst_aux []
-
- and sort_of_prod context (name,s) (t1, t2) =
-  let module C = Cic in
-   let t1' = CicReduction.whd context t1 in
-   let t2' = CicReduction.whd ((Some (name,C.Decl s))::context) t2 in
-   match (t1', t2') with
-      (C.Sort s1, C.Sort s2)
-        when (s2 = C.Prop or s2 = C.Set) -> (* different from Coq manual!!! *)
-         C.Sort s2
-    | (C.Sort s1, C.Sort s2) -> C.Sort C.Type (*CSC manca la gestione degli universi!!! *)
-    | (_,_) ->
-      raise
-       (TypeCheckerFailure
-        (NotWellTyped
-         ("Prod: sort1= " ^ CicPp.ppterm t1' ^ " ; sort2= "^ CicPp.ppterm t2')))
-
- and eat_prods context hetype =
-  (*CSC: siamo sicuri che le are_convertible non lavorino con termini non *)
-  (*CSC: cucinati                                                         *)
-  function
-     [] -> hetype
-   | (hete, hety)::tl ->
-    (match (CicReduction.whd context hetype) with
-        Cic.Prod (n,s,t) ->
-         if CicReduction.are_convertible context s hety then
-          (CicReduction.fdebug := -1 ;
-           eat_prods context (CicSubstitution.subst hete t) tl
-          )
-         else
-          begin
-           CicReduction.fdebug := 0 ;
-           ignore (CicReduction.are_convertible context s hety) ;
-           fdebug := 0 ;
-           debug s [hety] ;
-           raise
-            (TypeCheckerFailure (NotWellTyped "Appl: wrong parameter-type"))
-          end
-      | _ -> raise (TypeCheckerFailure (NotWellTyped "Appl: wrong Prod-type"))
-    )
-
- and returns_a_coinductive context ty =
-  let module C = Cic in
-   match CicReduction.whd context ty with
-      C.MutInd (uri,i,_) ->
-       (*CSC: definire una funzioncina per questo codice sempre replicato *)
-       (match CicEnvironment.get_cooked_obj ~trust:false uri with
-           C.InductiveDefinition (itl,_,_) ->
-            let (_,is_inductive,_,_) = List.nth itl i in
-             if is_inductive then None else (Some uri)
-         | _ ->
-           raise
-            (TypeCheckerFailure (WrongUriToMutualInductiveDefinitions
-             (UriManager.string_of_uri uri)))
-        )
-    | C.Appl ((C.MutInd (uri,i,_))::_) ->
-       (match CicEnvironment.get_obj uri with
-           C.InductiveDefinition (itl,_,_) ->
-            let (_,is_inductive,_,_) = List.nth itl i in
-             if is_inductive then None else (Some uri)
-         | _ ->
-           raise
-            (TypeCheckerFailure
-             (WrongUriToMutualInductiveDefinitions
-              (UriManager.string_of_uri uri)))
-        )
-    | C.Prod (n,so,de) ->
-       returns_a_coinductive ((Some (n,C.Decl so))::context) de
-    | _ -> None
-
- in
-(*CSC
-prerr_endline ("INIZIO TYPE_OF_AUX " ^ CicPp.ppterm t) ; flush stderr ;
-let res =
-*)
-  type_of_aux context t
-(*
-in prerr_endline "FINE TYPE_OF_AUX" ; flush stderr ; res
-*)
-
-(* is a small constructor? *)
-(*CSC: ottimizzare calcolando staticamente *)
-and is_small context paramsno c =
- let rec is_small_aux context c =
-  let module C = Cic in
-   match CicReduction.whd context c with
-      C.Prod (n,so,de) ->
-       (*CSC: [] is an empty metasenv. Is it correct? *)
-       let s = type_of_aux' [] context so in
-        (s = C.Sort C.Prop || s = C.Sort C.Set) &&
-        is_small_aux ((Some (n,(C.Decl so)))::context) de
-    | _ -> true (*CSC: we trust the type-checker *)
- in
-  let (context',dx) = split_prods context paramsno c in
-   is_small_aux context' dx
-
-and type_of t =
-(*CSC
-prerr_endline ("INIZIO TYPE_OF_AUX' " ^ CicPp.ppterm t) ; flush stderr ;
-let res =
-*)
- type_of_aux' [] [] t
-(*CSC
-in prerr_endline "FINE TYPE_OF_AUX'" ; flush stderr ; res
-*)
-;;
-
-let typecheck uri =
- let module C = Cic in
- let module R = CicReduction in
- let module U = UriManager in
-  match CicEnvironment.is_type_checked ~trust:false uri with
-     CicEnvironment.CheckedObj _ -> ()
-   | CicEnvironment.UncheckedObj uobj ->
-      (* let's typecheck the uncooked object *)
-      Logger.log (`Start_type_checking uri) ;
-      (match uobj with
-          C.Constant (_,Some te,ty,_) ->
-           let _ = type_of ty in
-            if not (R.are_convertible [] (type_of te ) ty) then
-             raise
-              (TypeCheckerFailure
-                (NotWellTyped ("Constant " ^ (U.string_of_uri uri))))
-        | C.Constant (_,None,ty,_) ->
-          (* only to check that ty is well-typed *)
-          let _ = type_of ty in ()
-        | C.CurrentProof (_,conjs,te,ty,_) ->
-           let _ =
-            List.fold_left
-             (fun metasenv ((_,context,ty) as conj) ->
-               ignore (type_of_aux' metasenv context ty) ;
-               metasenv @ [conj]
-             ) [] conjs
-           in
-            let _ = type_of_aux' conjs [] ty in
-             if not (R.are_convertible [] (type_of_aux' conjs [] te) ty)
-             then
-              raise
-               (TypeCheckerFailure
-                 (NotWellTyped ("CurrentProof" ^ (U.string_of_uri uri))))
-        | C.Variable (_,bo,ty,_) ->
-           (* only to check that ty is well-typed *)
-           let _ = type_of ty in
-            (match bo with
-                None -> ()
-              | Some bo ->
-                 if not (R.are_convertible [] (type_of bo) ty) then
-                  raise
-                   (TypeCheckerFailure
-                     (NotWellTyped ("Variable" ^ (U.string_of_uri uri))))
-            )
-        | C.InductiveDefinition _ ->
-           check_mutual_inductive_defs uri uobj
-      ) ;
-      CicEnvironment.set_type_checking_info uri ;
-      Logger.log (`Type_checking_completed uri)
-;;