Inductive expr_erase : expr W -> expr S' -> Prop :=
| erase_EVal : forall v,
     expr_erase (EVal _ v) (EVal _ v)
| erase_EUnop : forall op e e',
     expr_erase e e'
     -> expr_erase (EUnop op e) (EUnop op e')
| erase_EBinop : forall op e1 e2 e1' e2',
     expr_erase e1 e1'
     -> expr_erase e2 e2'
     -> expr_erase (EBinop op e1 e2) (EBinop op e1' e2')
| erase_EPrim : forall g f,
     GF g f
     -> expr_erase (EPrim g) (EPrim f).Inductive expr_erase : expr W -> expr S' -> Prop :=
| erase_EVal : forall v,
     expr_erase (EVal _ v) (EVal _ v)
| erase_EUnop : forall op e e',
     expr_erase e e'
     -> expr_erase (EUnop op e) (EUnop op e')
| erase_EBinop : forall op e1 e2 e1' e2',
     expr_erase e1 e1'
     -> expr_erase e2 e2'
     -> expr_erase (EBinop op e1 e2) (EBinop op e1' e2')
| erase_EPrim : forall g f,
     GF g f
     -> expr_erase (EPrim g) (EPrim f).Inductive expr_erase : expr W -> expr S' -> Prop :=
| erase_EVal : forall v,
     expr_erase (EVal _ v) (EVal _ v)
| erase_EUnop : forall op e e',
     expr_erase e e'
     -> expr_erase (EUnop op e) (EUnop op e')
| erase_EBinop : forall op e1 e2 e1' e2',
     expr_erase e1 e1'
     -> expr_erase e2 e2'
     -> expr_erase (EBinop op e1 e2) (EBinop op e1' e2')
| erase_EPrim : forall g f,
     GF g f
     -> expr_erase (EPrim g) (EPrim f).Inductive expr_erase : expr W -> expr S' -> Prop :=
| erase_EVal : forall v,
     expr_erase (EVal _ v) (EVal _ v)
| erase_EUnop : forall op e e',
     expr_erase e e'
     -> expr_erase (EUnop op e) (EUnop op e')
| erase_EBinop : forall op e1 e2 e1' e2',
     expr_erase e1 e1'
     -> expr_erase e2 e2'
     -> expr_erase (EBinop op e1 e2) (EBinop op e1' e2')
| erase_EPrim : forall g f,
     GF g f
     -> expr_erase (EPrim g) (EPrim f).Inductive expr_erase : expr W -> expr S' -> Prop :=
| erase_EVal : forall v,
     expr_erase (EVal _ v) (EVal _ v)
| erase_EUnop : forall op e e',
     expr_erase e e'
     -> expr_erase (EUnop op e) (EUnop op e')
| erase_EBinop : forall op e1 e2 e1' e2',
     expr_erase e1 e1'
     -> expr_erase e2 e2'
     -> expr_erase (EBinop op e1 e2) (EBinop op e1' e2')
| erase_EPrim : forall g f,
     GF g f
     -> expr_erase (EPrim g) (EPrim f).

Lemma expr_erase_pure_expr : forall e e', expr_erase e e' -> pure_expr _ e -> pure_expr _ e'.