(* calcul de l'état produit *)

Fixpoint s_produit_l (a : ad) (p : prec_list) (s : state) {struct s} :
 state :=
  match s with
  | M0 => M0 prec_list
  | M1 a' p' =>
      if Neqb a a' then M1 prec_list a (pl_produit p p') else M0 prec_list
  | M2 s0 s1 =>
      match a with
      | N0 => M2 prec_list (s_produit_l N0 p s0) (M0 prec_list)
      | Npos q =>
          match q with
          | xH => M2 prec_list (M0 prec_list) (s_produit_l N0 p s1)
          | xO q' => M2 prec_list (s_produit_l (Npos q') p s0) (M0 prec_list)
          | xI q' => M2 prec_list (M0 prec_list) (s_produit_l (Npos q') p s1)
          end
      end
  end.Definition sproductl_0_def (s : state) : Prop :=
  forall (a : ad) (p : prec_list) (c : ad) (r0 r1 : prec_list),
  MapGet prec_list (M1 prec_list a p) c = Some r0 ->
  MapGet prec_list s c = Some r1 ->
  MapGet prec_list (s_produit_l a p s) c = Some (pl_produit r0 r1).

(* Specifications: *)
Lemma sproductl_0_0 : sproductl_0_def (M0 prec_list).
Lemma sproductl_0_1 : forall (a : ad) (a0 : prec_list), sproductl_0_def (M1 prec_list a a0).
Lemma sproductl_0_2 : forall m : state, sproductl_0_def m -> forall m0 : state, sproductl_0_def m0 -> sproductl_0_def (M2 prec_list m m0).
Lemma sproductl_0_3 : forall m : state, sproductl_0_def m.
Lemma sproductl_0 : forall (s : state) (a : ad) (p : prec_list) (c : ad) (r0 r1 : prec_list), MapGet prec_list (M1 prec_list a p) c = Some r0 -> MapGet prec_list s c = Some r1 -> MapGet prec_list (s_produit_l a p s) c = Some (pl_produit r0 r1).