returns (field_offsets, size, align)
(
cx: &CodegenCx<'_>,
field_types: &[Word],
)
| 672 | |
| 673 | // returns (field_offsets, size, align) |
| 674 | pub fn auto_struct_layout( |
| 675 | cx: &CodegenCx<'_>, |
| 676 | field_types: &[Word], |
| 677 | ) -> (Vec<Size>, Option<Size>, Align) { |
| 678 | // FIXME(eddyb) use `AccumulateVec`s just like `rustc` itself does. |
| 679 | let mut field_offsets = Vec::with_capacity(field_types.len()); |
| 680 | let mut offset = Some(Size::ZERO); |
| 681 | let mut max_align = Align::from_bytes(0).unwrap(); |
| 682 | for &field_type in field_types { |
| 683 | let spirv_type = cx.lookup_type(field_type); |
| 684 | let field_size = spirv_type.sizeof(cx); |
| 685 | let field_align = spirv_type.alignof(cx); |
| 686 | let this_offset = offset |
| 687 | .expect("Unsized values can only be the last field in a struct") |
| 688 | .align_to(field_align); |
| 689 | |
| 690 | field_offsets.push(this_offset); |
| 691 | if field_align > max_align { |
| 692 | max_align = field_align; |
| 693 | } |
| 694 | offset = field_size.map(|size| this_offset + size); |
| 695 | } |
| 696 | (field_offsets, offset, max_align) |
| 697 | } |
| 698 | |
| 699 | // see struct_llfields in librustc_codegen_llvm for implementation hints |
| 700 | fn trans_struct<'tcx>(cx: &CodegenCx<'tcx>, span: Span, ty: TyAndLayout<'tcx>) -> Word { |
no test coverage detected