Library Imp_LangTrick.Tactics.AimpWfAndCheckProofAuto
Automation for aimp_wf proofs
From Coq Require Import Psatz Arith String List.
From Imp_LangTrick Require Import StackLanguage Imp_LangTrickLanguage Base rsa_impLang SeriesExample FunctionWellFormed EnvToStackLTtoLEQ TranslationPure ProofCompMod StackLangTheorems ParamsWellFormed Imp_LangImpHigherOrderRel Imp_LangImpHigherOrderRelTheorems Imp_LangDec Imp_LangLogPropDec UIPList CompilerAssumptionLogicTrans.
Local Open Scope list_scope.
Local Open Scope string_scope.
From Imp_LangTrick Require Import ProofCompAutoAnother BloomFilterArrayProgram.
From Imp_LangTrick Require Import LogicProp Imp_LangLogProp Imp_LangLogHoare ProofCompAuto ProofCompCodeCompAgnosticMod Imp_LangHoareWF ProofCompilerBase ImpHasVariableReflection FunctionWellFormedReflection.
Local Open Scope imp_langtrick_scope.
Ltac hl_Imp_Lang_wf_seq_helper :=
match goal with
| [ |- Imp_LangHoareWF.hl_Imp_Lang_wf ?fenv ?funcs ?idents ?num_args ?P ?Q (SEQ_Imp_Lang ?c1 ?c2) ?facts (hl_Imp_Lang_seq ?P' ?Q' ?R ?facts' ?fenv' ?c1' ?c2' ?hl1' ?hl2') ] =>
let Heq := fresh "Heq" in
assert (Heq : SEQ_Imp_Lang c1 c2 = SEQ_Imp_Lang c1' c2') by reflexivity || enough (Heq : SEQ_Imp_Lang c1 c2 = SEQ_Imp_Lang c1' c2');
let Heq_refl := fresh "Heq_refl" in
pose proof (Heq_refl := UIP_imp_refl _ Heq);
eapply Imp_LangHoareWF.HLImp_LangWFSeq with (Heq := Heq); [ rewrite Heq_refl; simpl; try reflexivity | clear Heq Heq_refl .. ]
end.
Ltac econstructor_prop_args_rel :=
repeat match goal with
| [ |- prop_args_rel _ _ ] =>
econstructor
end.
Ltac hl_Imp_Lang_wf_roc_pre_helper :=
match goal with
| [ |- Imp_LangHoareWF.hl_Imp_Lang_wf ?fenv ?funcs ?idents ?num_args ?precond ?postcond ?i ?facts (hl_Imp_Lang_consequence_pre ?P ?d ?d' ?i' ?n ?facts' ?fenv' ?hlP ?Hnth' ?aimp) ] =>
let Hnth := fresh "Hnth" in
assert (Hnth : let ele := nth n facts (true_precondition, true_precondition) in
nth_error facts n = Some (fst ele, snd ele)) by reflexivity;
pose proof (UIP_option_refl := UIP_option_pair_refl);
specialize (UIP_option_refl _ Imp_LangLogPropDec.UIP_AbsEnv);
specialize (UIP_option_refl _ Hnth);
eapply Imp_LangHoareWF.HLImp_LangWFConsequencePre with (nth := Hnth); [ | | try clear UIP_option_refl; try clear Hnth .. ]
end.
Ltac hl_imp_lang_wf_assign_helper :=
match goal with
| [ |- Imp_LangHoareWF.hl_Imp_Lang_wf ?fenv ?func_list ?idents ?num_args ?d ?d' (ASSIGN_Imp_Lang ?x ?a) ?facts (hl_Imp_Lang_assign ?d'' ?facts' ?fenv' ?x' ?a') ] =>
let Hsubst := fresh "Hsubst" in
let Heq := fresh "Heq" in
assert (Hsubst : Imp_LangLogSubst.subst_AbsEnv x a d' = d) by reflexivity || enough (Hsubst : Imp_LangLogSubst.subst_AbsEnv x a d' = d);
assert (Heq : ASSIGN_Imp_Lang x a = ASSIGN_Imp_Lang x' a') by reflexivity || enough (Heq: ASSIGN_Imp_Lang x a = ASSIGN_Imp_Lang x' a');
pose proof (Hsubstrefl := Imp_LangLogPropDec.UIP_AbsEnv_refl _ Hsubst);
pose proof (Heqrefl := UIP_imp_refl _ Heq);
eapply Imp_LangHoareWF.HLImp_LangWFAssign with (Heq := Heq) (Hsubst := Hsubst); [try rewrite Hsubstrefl; try rewrite Heqrefl; simpl; try reflexivity | clear Hsubstrefl Heqrefl; clear Heq Hsubst .. ]
end.
Ltac AbsEnv_prop_wf_nary_prop :=
match goal with
| [ |- ProofCompilerBase.AbsEnv_prop_wf ?idents ?P ] =>
match P with
| context P' [(NaryProp _ _ ?Q ?args)] =>
do 3 econstructor;
econstructor_prop_args_rel;
first [eapply CompilerCorrectHelpers.param_imp_lang_always_well_formed | eapply CompilerCorrectHelpers.const_imp_lang_always_well_formed | eapply ImpVarMapTheorems.var_map_wf_var_imp_lang | eapply CompilerCorrectHelpers.var_map_wf_wrt_aexp_subset ];
try first [finite_nodup | finite_in]
end
end.
Ltac deal_with_var_map_wf :=
match goal with
| [ |- var_map_wf_wrt_aexp ?idents ?a ] =>
first [eapply CompilerCorrectHelpers.param_imp_lang_always_well_formed | eapply CompilerCorrectHelpers.const_imp_lang_always_well_formed | eapply ImpVarMapTheorems.var_map_wf_var_imp_lang | eapply CompilerCorrectHelpers.var_map_wf_wrt_aexp_subset ];
cbn -[In];
try finite_nodup; try finite_in
| [ |- var_map_wf_wrt_bexp ?idents ?b ] =>
first [eapply CompilerCorrectHelpers.true_imp_lang_always_well_formed | eapply CompilerCorrectHelpers.false_imp_lang_always_well_formed | eapply CompilerCorrectMoreHelpers.var_map_wf_wrt_bexp_subset; [ unfold construct_trans; cbn -[In]; intros; finite_in_implication | .. ] ];
cbn -[In];
try finite_nodup; try finite_in
| [ |- imp_rec_rel (var_map_wf_wrt_imp ?idents) ?i ] =>
first [assert (idents = construct_trans i) by reflexivity;
eapply CompilerCorrectMoreHelpers.var_map_wf_imp_self_imp_rec_rel
| eapply CompilerCorrectMoreHelpers.var_map_wf_wrt_imp_subset_imp_rec_rel; [ try eapply CompilerCorrectMoreHelpers.var_map_wf_imp_self_imp_rec_rel; unfold construct_trans; cbn -[In]; reflexivity | intros; finite_in_implication | finite_nodup .. ] ]
end.
Ltac hl_Imp_Lang_wf_roc_post_helper :=
match goal with
| [ |- Imp_LangHoareWF.hl_Imp_Lang_wf ?fenv ?funcs ?idents ?num_args ?precond ?postcond ?i ?facts (hl_Imp_Lang_consequence_post ?d ?P ?d' ?i' ?n ?facts' ?fenv' ?hlP ?Hnth' ?aimp) ] =>
let Hnth := fresh "Hnth" in
assert (Hnth : let ele := nth n facts (true_precondition, true_precondition) in
nth_error facts n = Some (fst ele, snd ele)) by reflexivity;
pose proof (UIP_option_refl := UIP_option_pair_refl);
specialize (UIP_option_refl _ Imp_LangLogPropDec.UIP_AbsEnv);
specialize (UIP_option_refl _ Hnth);
eapply Imp_LangHoareWF.HLImp_LangWFConsequencePost with (nth := Hnth); [ rewrite UIP_option_refl; try reflexivity | | try clear UIP_option_refl; try clear Hnth .. ]
end.
Runs econstructor until you get to either
prop_rel or prop_args_rel.
Typically, you want to stop there, because it might start going into bad
cases from there on.
Ltac AbsEnv_prop_wf_helper :=
repeat match goal with
| [ |- prop_args_rel _ _ ] =>
fail 1
| [ |- prop_rel _ _ ] =>
fail 1
| [ |- ?sth _ ] =>
match sth with
| prop_args_rel =>
fail 2
| prop_rel =>
fail 2
| _ =>
econstructor
end
end;
repeat match goal with
| [ |- prop_args_rel _ _ ] =>
econstructor_prop_args_rel
| [ |- prop_rel _ _ ] =>
econstructor
end.
Ltac simplify_in := cbn -[In].
Ltac simplify_var_map_wf_cases :=
try ((AbsEnv_prop_wf_helper; deal_with_var_map_wf; cbn -[In]; intros) || deal_with_var_map_wf).
Ltac hl_wf_assign :=
hl_imp_lang_wf_assign_helper; simplify_var_map_wf_cases; repeat econstructor.
Ltac repeat_econstructor_on :=
repeat match goal with
| [ |- hl_Imp_Lang_wf _ _ _ _ _ _ _ _ _ ] =>
idtac
| [ |- AbsEnv_prop_wf _ _ ] =>
AbsEnv_prop_wf_helper; deal_with_var_map_wf
| [ |- imp_has_variable _ _ ] =>
prove_imp_has_variable
| [ |- fun_app_well_formed _ _ (APP_Imp_Lang _ _) ] =>
prove_fun_app_wf
| [ |- _ ] =>
econstructor
end.
Ltac hl_wf_seq_assign :=
hl_Imp_Lang_wf_seq_helper; simplify_var_map_wf_cases; [ hl_imp_lang_wf_assign_helper | ..]; simplify_var_map_wf_cases; repeat_econstructor_on.
Ltac handle_fun_app_well_formed_app :=
prove_fun_app_wf.
Ltac log_Imp_Lang_wf_helper_no_app := repeat_econstructor_on; handle_fun_app_well_formed_app.
Ltac hl_imp_lang_wf_while_helper :=
match goal with
| [ |- Imp_LangHoareWF.hl_Imp_Lang_wf ?fenv ?funcs ?idents ?args ?d ?d' (WHILE_Imp_Lang ?b ?while_body) ?facts (hl_Imp_Lang_while ?I ?b' ?while_body' ?facts' ?fenv' ?hl) ] =>
let HeqP := fresh "HeqP" in
let Heq := fresh "Heq" in
assert (HeqP : afalseImp_Lang b d = d') by reflexivity || enough (HeqP : afalseImp_Lang b d = d');
assert (Heq : WHILE_Imp_Lang b while_body = WHILE_Imp_Lang b' while_body') by reflexivity || enough (Heq: WHILE_Imp_Lang b while_body = WHILE_Imp_Lang b' while_body');
pose proof (HeqPrefl := Imp_LangLogPropDec.UIP_AbsEnv_refl _ HeqP);
pose proof (Heqrefl := UIP_imp_refl _ Heq);
eapply Imp_LangHoareWF.HLImp_LangWFWhile with (Heq := Heq) (HeqP := HeqP); [try rewrite HeqPrefl; try rewrite Heqrefl; simpl; try reflexivity | clear HeqPrefl Heqrefl; clear Heq HeqP .. ]
end.
Ltac program_subset_imp_rec_rel_var_map_wf :=
match goal with
| [ |- imp_rec_rel (var_map_wf_wrt_imp _) _ ] =>
eapply CompilerCorrectMoreHelpers.var_map_wf_wrt_imp_subset_imp_rec_rel; cbn -[In];
[ eapply CompilerCorrectMoreHelpers.var_map_wf_imp_self_imp_rec_rel; reflexivity
| cbn -[In]; intros; finite_in_implication
| cbn; finite_nodup_reflective .. ]
end.
Ltac smash_other_cases :=
repeat match goal with
| [ |- log_Imp_Lang_wf _ _ _ ] =>
try log_Imp_Lang_wf_helper_no_app
| [ |- log_Imp_Lang_wf_map _ _ ] =>
simplify_var_map_wf_cases
| [ |- AbsEnv_prop_rel (all_params_ok_aexp _)
(all_params_ok_bexp _) _ ] =>
repeat_econstructor_on
| [ |- ProofCompilerBase.AbsEnv_prop_wf _ _ ] =>
simplify_var_map_wf_cases
| [ |- imp_rec_rel (var_map_wf_wrt_imp _) _ ] =>
try (solve [deal_with_var_map_wf | program_subset_imp_rec_rel_var_map_wf ])
| [ |- fun_app_well_formed _ _ _ ] =>
try FunctionWellFormedReflection.prove_fun_app_wf
| [ |- _ ] => idtac
end.
Ltac hl_Imp_Lang_wf_if_helper :=
match goal with
| [ |- hl_Imp_Lang_wf ?fenv ?funcs ?idents ?args ?d ?d' (IF_Imp_Lang ?b ?i1 ?i2) _ (hl_Imp_Lang_if ?P ?Q ?b' ?i1' ?i2' ?fact_env ?fenv' ?HLtrue ?HLfalse) ] =>
let heq := fresh "heq" in
assert (heq : IF_Imp_Lang b i1 i2 = IF_Imp_Lang b' i1' i2') by reflexivity;
let Himp_uip := fresh "Himp_uip" in
pose proof (Himp_uip := UIP_imp_refl _ heq);
eapply HLImp_LangWFIf with (heq := heq); try rewrite Himp_uip; try simpl; try reflexivity; try (clear Himp_uip; clear heq)
end.
repeat match goal with
| [ |- prop_args_rel _ _ ] =>
fail 1
| [ |- prop_rel _ _ ] =>
fail 1
| [ |- ?sth _ ] =>
match sth with
| prop_args_rel =>
fail 2
| prop_rel =>
fail 2
| _ =>
econstructor
end
end;
repeat match goal with
| [ |- prop_args_rel _ _ ] =>
econstructor_prop_args_rel
| [ |- prop_rel _ _ ] =>
econstructor
end.
Ltac simplify_in := cbn -[In].
Ltac simplify_var_map_wf_cases :=
try ((AbsEnv_prop_wf_helper; deal_with_var_map_wf; cbn -[In]; intros) || deal_with_var_map_wf).
Ltac hl_wf_assign :=
hl_imp_lang_wf_assign_helper; simplify_var_map_wf_cases; repeat econstructor.
Ltac repeat_econstructor_on :=
repeat match goal with
| [ |- hl_Imp_Lang_wf _ _ _ _ _ _ _ _ _ ] =>
idtac
| [ |- AbsEnv_prop_wf _ _ ] =>
AbsEnv_prop_wf_helper; deal_with_var_map_wf
| [ |- imp_has_variable _ _ ] =>
prove_imp_has_variable
| [ |- fun_app_well_formed _ _ (APP_Imp_Lang _ _) ] =>
prove_fun_app_wf
| [ |- _ ] =>
econstructor
end.
Ltac hl_wf_seq_assign :=
hl_Imp_Lang_wf_seq_helper; simplify_var_map_wf_cases; [ hl_imp_lang_wf_assign_helper | ..]; simplify_var_map_wf_cases; repeat_econstructor_on.
Ltac handle_fun_app_well_formed_app :=
prove_fun_app_wf.
Ltac log_Imp_Lang_wf_helper_no_app := repeat_econstructor_on; handle_fun_app_well_formed_app.
Ltac hl_imp_lang_wf_while_helper :=
match goal with
| [ |- Imp_LangHoareWF.hl_Imp_Lang_wf ?fenv ?funcs ?idents ?args ?d ?d' (WHILE_Imp_Lang ?b ?while_body) ?facts (hl_Imp_Lang_while ?I ?b' ?while_body' ?facts' ?fenv' ?hl) ] =>
let HeqP := fresh "HeqP" in
let Heq := fresh "Heq" in
assert (HeqP : afalseImp_Lang b d = d') by reflexivity || enough (HeqP : afalseImp_Lang b d = d');
assert (Heq : WHILE_Imp_Lang b while_body = WHILE_Imp_Lang b' while_body') by reflexivity || enough (Heq: WHILE_Imp_Lang b while_body = WHILE_Imp_Lang b' while_body');
pose proof (HeqPrefl := Imp_LangLogPropDec.UIP_AbsEnv_refl _ HeqP);
pose proof (Heqrefl := UIP_imp_refl _ Heq);
eapply Imp_LangHoareWF.HLImp_LangWFWhile with (Heq := Heq) (HeqP := HeqP); [try rewrite HeqPrefl; try rewrite Heqrefl; simpl; try reflexivity | clear HeqPrefl Heqrefl; clear Heq HeqP .. ]
end.
Ltac program_subset_imp_rec_rel_var_map_wf :=
match goal with
| [ |- imp_rec_rel (var_map_wf_wrt_imp _) _ ] =>
eapply CompilerCorrectMoreHelpers.var_map_wf_wrt_imp_subset_imp_rec_rel; cbn -[In];
[ eapply CompilerCorrectMoreHelpers.var_map_wf_imp_self_imp_rec_rel; reflexivity
| cbn -[In]; intros; finite_in_implication
| cbn; finite_nodup_reflective .. ]
end.
Ltac smash_other_cases :=
repeat match goal with
| [ |- log_Imp_Lang_wf _ _ _ ] =>
try log_Imp_Lang_wf_helper_no_app
| [ |- log_Imp_Lang_wf_map _ _ ] =>
simplify_var_map_wf_cases
| [ |- AbsEnv_prop_rel (all_params_ok_aexp _)
(all_params_ok_bexp _) _ ] =>
repeat_econstructor_on
| [ |- ProofCompilerBase.AbsEnv_prop_wf _ _ ] =>
simplify_var_map_wf_cases
| [ |- imp_rec_rel (var_map_wf_wrt_imp _) _ ] =>
try (solve [deal_with_var_map_wf | program_subset_imp_rec_rel_var_map_wf ])
| [ |- fun_app_well_formed _ _ _ ] =>
try FunctionWellFormedReflection.prove_fun_app_wf
| [ |- _ ] => idtac
end.
Ltac hl_Imp_Lang_wf_if_helper :=
match goal with
| [ |- hl_Imp_Lang_wf ?fenv ?funcs ?idents ?args ?d ?d' (IF_Imp_Lang ?b ?i1 ?i2) _ (hl_Imp_Lang_if ?P ?Q ?b' ?i1' ?i2' ?fact_env ?fenv' ?HLtrue ?HLfalse) ] =>
let heq := fresh "heq" in
assert (heq : IF_Imp_Lang b i1 i2 = IF_Imp_Lang b' i1' i2') by reflexivity;
let Himp_uip := fresh "Himp_uip" in
pose proof (Himp_uip := UIP_imp_refl _ heq);
eapply HLImp_LangWFIf with (heq := heq); try rewrite Himp_uip; try simpl; try reflexivity; try (clear Himp_uip; clear heq)
end.