--- /dev/null
+(**************************************************************************)
+(* ___ *)
+(* ||M|| *)
+(* ||A|| A project by Andrea Asperti *)
+(* ||T|| *)
+(* ||I|| Developers: *)
+(* ||T|| The HELM team. *)
+(* ||A|| http://helm.cs.unibo.it *)
+(* \ / *)
+(* \ / This file is distributed under the terms of the *)
+(* v GNU General Public License Version 2 *)
+(* *)
+(**************************************************************************)
+
+(* ********************************************************************** *)
+(* Progetto FreeScale *)
+(* *)
+(* Sviluppato da: Cosimo Oliboni, oliboni@cs.unibo.it *)
+(* Cosimo Oliboni, oliboni@cs.unibo.it *)
+(* *)
+(* ********************************************************************** *)
+
+include "compiler/ast_type.ma".
+
+(* ************************* *)
+(* dimensioni degli elementi *)
+(* ************************* *)
+
+ndefinition astbasetype_destruct_aux ≝
+Πb1,b2:ast_base_type.ΠP:Prop.b1 = b2 →
+ match b1 with
+ [ AST_BASE_TYPE_BYTE8 ⇒ match b2 with [ AST_BASE_TYPE_BYTE8 ⇒ P → P | _ ⇒ P ]
+ | AST_BASE_TYPE_WORD16 ⇒ match b2 with [ AST_BASE_TYPE_WORD16 ⇒ P → P | _ ⇒ P ]
+ | AST_BASE_TYPE_WORD32 ⇒ match b2 with [ AST_BASE_TYPE_WORD32 ⇒ P → P | _ ⇒ P ]
+ ].
+
+ndefinition astbasetype_destruct : astbasetype_destruct_aux.
+ #b1; #b2; #P;
+ nelim b1;
+ nelim b2;
+ nnormalize;
+ #H;
+ ##[ ##1,5,9: napply (λx:P.x)
+ ##| ##2,3: napply (False_ind ??);
+ nchange with (match AST_BASE_TYPE_BYTE8 with [ AST_BASE_TYPE_BYTE8 ⇒ False | _ ⇒ True]);
+ nrewrite > H;
+ nnormalize;
+ napply I
+ ##| ##4,6: napply (False_ind ??);
+ nchange with (match AST_BASE_TYPE_WORD16 with [ AST_BASE_TYPE_WORD16 ⇒ False | _ ⇒ True]);
+ nrewrite > H;
+ nnormalize;
+ napply I
+ ##| ##7,8: napply (False_ind ??);
+ nchange with (match AST_BASE_TYPE_WORD32 with [ AST_BASE_TYPE_WORD32 ⇒ False | _ ⇒ True]);
+ nrewrite > H;
+ nnormalize;
+ napply I
+ ##]
+nqed.
+
+nlemma symmetric_eqastbasetype : symmetricT ast_base_type bool eq_ast_base_type.
+ #b1; #b2; ncases b1; ncases b2; nnormalize; napply (refl_eq ??). nqed.
+
+nlemma eqastbasetype_to_eq : ∀b1,b2.eq_ast_base_type b1 b2 = true → b1 = b2.
+ #b1; #b2; ncases b1; ncases b2; nnormalize;
+ ##[ ##1,5,9: #H; napply (refl_eq ??)
+ ##| ##*: #H; napply (bool_destruct ??? H)
+ ##]
+nqed.
+
+nlemma eq_to_eqastbasetype : ∀b1,b2.b1 = b2 → eq_ast_base_type b1 b2 = true.
+ #b1; #b2; ncases b1; ncases b2; nnormalize;
+ ##[ ##1,5,9: #H; napply (refl_eq ??)
+ ##| ##*: #H; napply (astbasetype_destruct ??? H)
+ ##]
+nqed.
+
+nlemma asttype_destruct_base_base : ∀b1,b2.AST_TYPE_BASE b1 = AST_TYPE_BASE b2 → b1 = b2.
+ #b1; #b2; #H;
+ nchange with (match AST_TYPE_BASE b2 with [ AST_TYPE_BASE a ⇒ b1 = a | _ ⇒ False ]);
+ nrewrite < H;
+ nnormalize;
+ napply (refl_eq ??).
+nqed.
+
+nlemma asttype_destruct_array_array_1 : ∀x1,x2,y1,y2.AST_TYPE_ARRAY x1 y1 = AST_TYPE_ARRAY x2 y2 → x1 = x2.
+ #x1; #x2; #y1; #y2; #H;
+ nchange with (match AST_TYPE_ARRAY x2 y2 with [ AST_TYPE_ARRAY a _ ⇒ x1 = a | _ ⇒ False ]);
+ nrewrite < H;
+ nnormalize;
+ napply (refl_eq ??).
+nqed.
+
+nlemma asttype_destruct_array_array_2 : ∀x1,x2,y1,y2.AST_TYPE_ARRAY x1 y1 = AST_TYPE_ARRAY x2 y2 → y1 = y2.
+ #x1; #x2; #y1; #y2; #H;
+ nchange with (match AST_TYPE_ARRAY x2 y2 with [ AST_TYPE_ARRAY _ b ⇒ y1 = b | _ ⇒ False ]);
+ nrewrite < H;
+ nnormalize;
+ napply (refl_eq ??).
+nqed.
+
+nlemma asttype_destruct_struc_struct : ∀b1,b2.AST_TYPE_STRUCT b1 = AST_TYPE_STRUCT b2 → b1 = b2.
+ #b1; #b2; #H;
+ nchange with (match AST_TYPE_STRUCT b2 with [ AST_TYPE_STRUCT a ⇒ b1 = a | _ ⇒ False ]);
+ nrewrite < H;
+ nnormalize;
+ napply (refl_eq ??).
+nqed.
+
+ndefinition asttype_destruct_aux ≝
+Πb1,b2:ast_type.ΠP:Prop.b1 = b2 →
+ match b1 with
+ [ AST_TYPE_BASE s1 ⇒ match b2 with
+ [ AST_TYPE_BASE s2 ⇒ match s1 with
+ [ AST_BASE_TYPE_BYTE8 ⇒ match s2 with [ AST_BASE_TYPE_BYTE8 ⇒ P → P | _ ⇒ P ]
+ | AST_BASE_TYPE_WORD16 ⇒ match s2 with [ AST_BASE_TYPE_WORD16 ⇒ P → P | _ ⇒ P ]
+ | AST_BASE_TYPE_WORD32 ⇒ match s2 with [ AST_BASE_TYPE_WORD32 ⇒ P → P | _ ⇒ P ]
+ ] | _ ⇒ P ]
+ | AST_TYPE_ARRAY _ _ ⇒ match b2 with [ AST_TYPE_ARRAY _ _ ⇒ P → P | _ ⇒ P ]
+ | AST_TYPE_STRUCT _ ⇒ match b2 with [ AST_TYPE_STRUCT _ ⇒ P → P | _ ⇒ P ]
+ ].
+
+ndefinition asttype_destruct : asttype_destruct_aux.
+ #b1; #b2; #P;
+ ncases b1;
+ ##[ ##1: ncases b2;
+ ##[ ##1: nnormalize; #s1; #s2; ncases s1; ncases s2; nnormalize;
+ ##[ ##1,5,9: #H; napply (λx:P.x)
+ ##| ##*: #H; napply (astbasetype_destruct ??? (asttype_destruct_base_base ?? H))
+ ##]
+ ##| ##2: #t; #n; #b; nnormalize; #H
+ ##| ##3: #l; #b; nnormalize; #H
+ ##]
+ napply (False_ind ??);
+ nchange with (match AST_TYPE_BASE b with [ AST_TYPE_BASE _ ⇒ False | _ ⇒ True ]);
+ nrewrite > H; nnormalize; napply I
+ ##| ##2: ncases b2;
+ ##[ ##2: #t1; #n1; #t2; #n2; nnormalize; #H; napply (λx:P.x)
+ ##| ##1: #b; #t; #n; nnormalize; #H
+ ##| ##3: #l; #t; #n; nnormalize; #H
+ ##]
+ napply (False_ind ??);
+ nchange with (match AST_TYPE_ARRAY t n with [ AST_TYPE_ARRAY _ _ ⇒ False | _ ⇒ True ]);
+ nrewrite > H; nnormalize; napply I
+ ##| ##3: ncases b2;
+ ##[ ##3: #l1; #l2; nnormalize; #H; napply (λx:P.x)
+ ##| ##1: #b; #l; nnormalize; #H
+ ##| ##2: #t; #n; #l; nnormalize; #H
+ ##]
+ napply (False_ind ??);
+ nchange with (match AST_TYPE_STRUCT l with [ AST_TYPE_STRUCT _ ⇒ False | _ ⇒ True ]);
+ nrewrite > H; nnormalize; napply I
+ ##]
+nqed.
+
+(* eq_ast lemmas missing *)
+
+nlemma isbastbasetype_to_isastbasetype : ∀ast.isb_ast_base_type ast = true → is_ast_base_type ast.
+ #ast;
+ ncases ast;
+ nnormalize;
+ ##[ ##1: #t; #H; napply I
+ ##| ##2: #t; #n; #H; napply (bool_destruct ??? H)
+ ##| ##3: #t; #H; napply (bool_destruct ??? H)
+ ##]
+nqed.
+
+nlemma isntbastbasetype_to_isntastbasetype : ∀ast.isntb_ast_base_type ast = true → isnt_ast_base_type ast.
+ #ast;
+ ncases ast;
+ nnormalize;
+ ##[ ##1: #t; #H; napply (bool_destruct ??? H)
+ ##| ##2: #t; #n; #H; napply I
+ ##| ##3: #l; #H; napply I
+ ##]
+nqed.