Skip to content

Commit 50694f2

Browse files
Pat Hickeypchickey
authored andcommitted
layout: fix bugs, clean up exports
1 parent 63e63ad commit 50694f2

File tree

2 files changed

+43
-27
lines changed

2 files changed

+43
-27
lines changed

tools/witx/src/layout.rs

Lines changed: 41 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -23,14 +23,14 @@ impl TypeRef {
2323
return *hit;
2424
}
2525
let layout = match &*self.type_() {
26-
Type::Enum(e) => e.repr.layout(),
27-
Type::Flags(f) => f.repr.layout(),
26+
Type::Enum(e) => e.repr.mem_size_align(),
27+
Type::Flags(f) => f.repr.mem_size_align(),
2828
Type::Struct(s) => s.layout(cache),
2929
Type::Union(u) => u.layout(cache),
30-
Type::Handle { .. } => BuiltinType::U32.layout(),
31-
Type::Array { .. } => BuiltinType::String.layout(),
32-
Type::Pointer { .. } | Type::ConstPointer { .. } => BuiltinType::U32.layout(),
33-
Type::Builtin(b) => b.layout(),
30+
Type::Handle { .. } => BuiltinType::U32.mem_size_align(),
31+
Type::Array { .. } => BuiltinType::String.mem_size_align(),
32+
Type::Pointer { .. } | Type::ConstPointer { .. } => BuiltinType::U32.mem_size_align(),
33+
Type::Builtin(b) => b.mem_size_align(),
3434
};
3535
cache.insert(self.clone(), layout);
3636
layout
@@ -43,28 +43,28 @@ impl Layout for TypeRef {
4343
self.layout(&mut cache)
4444
}
4545
}
46-
47-
impl IntRepr {
48-
pub fn layout(&self) -> SizeAlign {
46+
impl Layout for IntRepr {
47+
fn mem_size_align(&self) -> SizeAlign {
4948
match self {
50-
IntRepr::U8 => BuiltinType::U8.layout(),
51-
IntRepr::U16 => BuiltinType::U16.layout(),
52-
IntRepr::U32 => BuiltinType::U32.layout(),
53-
IntRepr::U64 => BuiltinType::U64.layout(),
49+
IntRepr::U8 => BuiltinType::U8.mem_size_align(),
50+
IntRepr::U16 => BuiltinType::U16.mem_size_align(),
51+
IntRepr::U32 => BuiltinType::U32.mem_size_align(),
52+
IntRepr::U64 => BuiltinType::U64.mem_size_align(),
5453
}
5554
}
5655
}
5756

5857
pub struct StructMemberLayout<'a> {
59-
member: &'a StructMember,
60-
offset: usize,
58+
pub member: &'a StructMember,
59+
pub offset: usize,
6160
}
6261

6362
impl StructDatatype {
64-
pub fn member_layout(
65-
&self,
66-
cache: &mut HashMap<TypeRef, SizeAlign>,
67-
) -> Vec<StructMemberLayout> {
63+
pub fn member_layout(&self) -> Vec<StructMemberLayout> {
64+
self.member_layout_(&mut HashMap::new())
65+
}
66+
67+
fn member_layout_(&self, cache: &mut HashMap<TypeRef, SizeAlign>) -> Vec<StructMemberLayout> {
6868
let mut members = Vec::new();
6969
let mut offset = 0;
7070
for m in self.members.iter() {
@@ -76,19 +76,27 @@ impl StructDatatype {
7676
members
7777
}
7878

79-
pub fn layout(&self, cache: &mut HashMap<TypeRef, SizeAlign>) -> SizeAlign {
80-
let members = self.member_layout(cache);
79+
fn layout(&self, cache: &mut HashMap<TypeRef, SizeAlign>) -> SizeAlign {
80+
let members = self.member_layout_(cache);
8181
let align = members
8282
.iter()
8383
.map(|m| m.member.tref.layout(cache).align)
8484
.max()
8585
.expect("nonzero struct members");
86-
let last_offset = members.last().expect("nonzero struct members").offset;
87-
let size = align_to(last_offset, align);
86+
let last = members.last().expect("nonzero struct members");
87+
let size = last.offset + last.member.tref.layout(cache).size;
88+
let size = align_to(size, align);
8889
SizeAlign { size, align }
8990
}
9091
}
9192

93+
impl Layout for StructDatatype {
94+
fn mem_size_align(&self) -> SizeAlign {
95+
let mut cache = HashMap::new();
96+
self.layout(&mut cache)
97+
}
98+
}
99+
92100
/// If the next free byte in the struct is `offs`, and the next
93101
/// element has alignment `alignment`, determine the offset at
94102
/// which to place that element.
@@ -124,7 +132,7 @@ mod test {
124132
}
125133

126134
impl UnionDatatype {
127-
pub fn layout(&self, cache: &mut HashMap<TypeRef, SizeAlign>) -> SizeAlign {
135+
fn layout(&self, cache: &mut HashMap<TypeRef, SizeAlign>) -> SizeAlign {
128136
let sas = self
129137
.variants
130138
.iter()
@@ -144,8 +152,15 @@ impl UnionDatatype {
144152
}
145153
}
146154

147-
impl BuiltinType {
148-
pub fn layout(&self) -> SizeAlign {
155+
impl Layout for UnionDatatype {
156+
fn mem_size_align(&self) -> SizeAlign {
157+
let mut cache = HashMap::new();
158+
self.layout(&mut cache)
159+
}
160+
}
161+
162+
impl Layout for BuiltinType {
163+
fn mem_size_align(&self) -> SizeAlign {
149164
match self {
150165
BuiltinType::String => SizeAlign { size: 8, align: 4 }, // Pointer and Length
151166
BuiltinType::U8 | BuiltinType::S8 => SizeAlign { size: 1, align: 1 },

tools/witx/src/lib.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ mod docs;
77
/// Interface for filesystem or mock IO
88
mod io;
99
/// Calculate memory layout of types
10-
pub mod layout;
10+
mod layout;
1111
/// Witx syntax parsing from SExprs
1212
mod parser;
1313
/// Calculate required polyfill between interfaces
@@ -31,6 +31,7 @@ pub use ast::{
3131
pub use coretypes::{AtomType, CoreFuncType, CoreParamSignifies, CoreParamType, TypePassedBy};
3232
pub use docs::Documentation;
3333
pub use io::{Filesystem, MockFs, WitxIo};
34+
pub use layout::{Layout, SizeAlign, StructMemberLayout};
3435
pub use parser::DeclSyntax;
3536
pub use render::SExpr;
3637
pub use representation::{RepEquality, Representable};

0 commit comments

Comments
 (0)