Inductive tree : Type :=
  | atom : A -> tree
  | node : list tree -> tree
  .Inductive tree : Type :=
  | atom : A -> tree
  | node : list tree -> tree
  .Inductive tree : Type :=
  | atom : A -> tree
  | node : list tree -> tree
  .Fixpoint tree_rect (t : tree) : P t :=
      let fix go_list (l : list tree) : P_list l :=
          match l with
          | [] => P_nil
          | t :: l => P_cons (tree_rect t) (go_list l)
          end
      in
      match t with
      | atom a => P_atom a
      | node l => P_node (go_list l)
      end.Definition tree_ind (t : tree) : P t :=
      tree_rect P (List.Forall P)
                (List.Forall_nil _)
                (fun t l Pt Pl => List.Forall_cons _ Pt Pl) P_atom P_node t.Fixpoint rev_rec {A} (l : list A) (acc : list A) :=
  match l with
  | [] => acc
  | a :: l => rev_rec l (a :: acc)
  end.

Lemma rev_rec_spec : forall {A : Type} (l : list A) acc, rev_rec l acc = rev l ++ acc.