+ (try
+ let name, ctx, term, ty = NCicUtils.lookup_subst i subst in
+ let term = eta_reduce subst term in
+ let subst = List.filter (fun (j,_) -> j <> i) subst in
+ metasenv, ((i, (name, ctx, term, ty)) :: subst)
+ with Not_found -> assert false))
+
+ | C.Meta (n,lc), t when List.mem_assoc n subst ->
+ let _,_,term,_ = NCicUtils.lookup_subst n subst in
+ let term = NCicSubstitution.subst_meta lc term in
+ unify rdb test_eq_only metasenv subst context term t
+
+ | t, C.Meta (n,lc) when List.mem_assoc n subst ->
+ let _,_,term,_ = NCicUtils.lookup_subst n subst in
+ let term = NCicSubstitution.subst_meta lc term in
+ unify rdb test_eq_only metasenv subst context t term
+
+ | NCic.Appl (NCic.Meta (i,l)::args), _ when List.mem_assoc i subst ->
+ let _,_,term,_ = NCicUtils.lookup_subst i subst in
+ let term = NCicSubstitution.subst_meta l term in
+ unify rdb test_eq_only metasenv subst context
+ (mk_appl ~upto:(List.length args) term args) t2
+
+ | _, NCic.Appl (NCic.Meta (i,l)::args) when List.mem_assoc i subst ->
+ let _,_,term,_ = NCicUtils.lookup_subst i subst in
+ let term = NCicSubstitution.subst_meta l term in
+ unify rdb test_eq_only metasenv subst context t1
+ (mk_appl ~upto:(List.length args) term args)
+
+ | C.Meta (n,lc), t ->
+ instantiate rdb test_eq_only metasenv subst context n lc
+ (NCicReduction.head_beta_reduce ~subst t) false
+
+ | t, C.Meta (n,lc) ->
+ instantiate rdb test_eq_only metasenv subst context n lc
+ (NCicReduction.head_beta_reduce ~subst t) true
+
+ | NCic.Appl (NCic.Meta (i,l) as meta :: args), _ ->
+ let metasenv, lambda_Mj =
+ lambda_intros rdb metasenv subst context (List.length args)
+ (NCicTypeChecker.typeof ~metasenv ~subst context meta)
+ in
+ let metasenv, subst =
+ try
+ unify rdb test_eq_only metasenv subst context
+ (C.Meta (i,l)) lambda_Mj
+ with UnificationFailure msg | Uncertain msg when not norm2->
+ (* failure: let's try again argument vs argument *)
+ raise (KeepReducing msg)
+ in
+ let metasenv, subst =
+ unify rdb test_eq_only metasenv subst context t1 t2
+ in
+ (try
+ let name, ctx, term, ty = NCicUtils.lookup_subst i subst in
+ let term = eta_reduce subst term in
+ let subst = List.filter (fun (j,_) -> j <> i) subst in
+ metasenv, ((i, (name, ctx, term, ty)) :: subst)
+ with Not_found -> assert false)
+
+ | _, NCic.Appl (NCic.Meta (i,l) as meta :: args) ->
+ let metasenv, lambda_Mj =
+ lambda_intros rdb metasenv subst context (List.length args)
+ (NCicTypeChecker.typeof ~metasenv ~subst context meta)
+ in
+ let metasenv, subst =
+ try
+ unify rdb test_eq_only metasenv subst context
+ lambda_Mj (C.Meta (i,l))
+ with UnificationFailure msg | Uncertain msg when not norm1 ->
+ (* failure: let's try again argument vs argument *)
+ raise (KeepReducing msg)
+ in
+ let metasenv, subst =
+ unify rdb test_eq_only metasenv subst context t1 t2
+ in
+ (try
+ let name, ctx, term, ty = NCicUtils.lookup_subst i subst in
+ let term = eta_reduce subst term in
+ let subst = List.filter (fun (j,_) -> j <> i) subst in
+ metasenv, ((i, (name, ctx, term, ty)) :: subst)
+ with Not_found -> assert false)