(** Type ranks *)
(** The rank of a type is a nonnegative integer that measures the direct nesting of arrays, struct and union types.  It does not take into account indirect nesting such as a struct type that appears under a pointer or function type. Type ranks ensure that type expressions (ignoring pointer and function types) have an inductive structure. *)
Fixpoint rank_type (ce: composite_env) (t: type) : nat :=
match t with
| Tarray t' _ _ => S (rank_type ce t')
| Tstruct id _ | Tunion id _ =>
match ce!id with
| None => O
| Some co => S (co_rank co)
end
| _ => O
end.
Fixpoint rank_members (ce: composite_env) (m: members) : nat :=
match m with
| nil => 0%nat
| (id, t) :: m => Init.Nat.max (rank_type ce t) (rank_members ce m)
end.
(** ** C types and back-end types *)
(** Extracting a type list from a function parameter declaration. *)
Fixpoint type_of_params (params: list (ident * type)) : typelist :=
match params with
| nil => Tnil
| (id, ty) :: rem => Tcons ty (type_of_params rem)
end.
(** Translating C types to Cminor types and function signatures. *)
Definition typ_of_type (t: type) : AST.typ :=
match t with
| Tvoid => AST.Tint
| Tint _ _ _ => AST.Tint
| Tlong _ _ => AST.Tlong
| Tfloat F32 _ => AST.Tsingle
| Tfloat F64 _ => AST.Tfloat
| Tpointer _ _ | Tarray _ _ _ | Tfunction _ _ _ | Tstruct _ _ | Tunion _ _ => AST.Tptr
end.
Definition opttyp_of_type (t: type) : option AST.typ :=
if type_eq t Tvoid then None else Some (typ_of_type t).
Fixpoint typlist_of_typelist (tl: typelist) : list AST.typ :=
match tl with
| Tnil => nil
| Tcons hd tl => typ_of_type hd :: typlist_of_typelist tl
end.
Definition signature_of_type (args: typelist) (res: type) (cc: calling_convention): signature :=
mksignature (typlist_of_typelist args) (opttyp_of_type res) cc.
(** * Construction of the composite environment *)
Definition sizeof_composite (env: composite_env) (su: struct_or_union) (m: members) : Z :=
match su with
| Struct => sizeof_struct env 0 m
| Union  => sizeof_union env m
end.

Lemma sizeof_composite_pos:
forall env su m, 0 <= sizeof_composite env su m.