Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Expose abi encoding #266

Merged
merged 1 commit into from
Feb 24, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion analyzer/src/namespace/operations.rs
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ mod tests {

const U256_ARRAY_TYPE: Type = Type::Array(Array {
inner: U256,
dimension: 100,
size: 100,
});
const U256_TYPE: Type = Type::Base(U256);
const BOOL_TYPE: Type = Type::Base(Base::Bool);
Expand Down
63 changes: 40 additions & 23 deletions analyzer/src/namespace/types.rs
Original file line number Diff line number Diff line change
Expand Up @@ -62,8 +62,13 @@ pub enum AbiType {
inner: Box<AbiType>,
size: AbiArraySize,
},
Tuple {
elems: Vec<AbiType>,
},
/// All elements are encoded as a uint or set of uints.
Uint { size: AbiUintSize },
Uint {
size: AbiUintSize,
},
}

/// Data can be decoded from memory or calldata.
Expand Down Expand Up @@ -144,7 +149,7 @@ pub const U256: Base = Base::Numeric(Integer::U256);

#[derive(Clone, Debug, PartialEq, PartialOrd, Ord, Eq)]
pub struct Array {
pub dimension: usize,
pub size: usize,
pub inner: Base,
}

Expand All @@ -162,7 +167,7 @@ pub struct Tuple {
#[derive(Clone, Debug, PartialEq, PartialOrd, Ord, Eq)]
pub struct Struct {
pub name: String,
fields: BTreeMap<String, Base>,
fields: BTreeMap<String, FixedSize>,
order: Vec<String>,
}

Expand Down Expand Up @@ -192,13 +197,13 @@ impl Struct {
}

/// Add a field to the struct
pub fn add_field(&mut self, name: &str, value: &Base) -> Option<Base> {
pub fn add_field(&mut self, name: &str, value: &FixedSize) -> Option<FixedSize> {
self.order.push(name.to_string());
self.fields.insert(name.to_string(), value.clone())
}

/// Return the type of the given field name
pub fn get_field_type(&self, name: &str) -> Option<&Base> {
pub fn get_field_type(&self, name: &str) -> Option<&FixedSize> {
self.fields.get(name)
}

Expand All @@ -208,15 +213,13 @@ impl Struct {
}

/// Return a vector of field types
pub fn get_field_types(&self) -> Vec<Type> {
pub fn get_field_types(&self) -> Vec<FixedSize> {
self.order
.iter()
.map(|name| {
Type::Base(
self.get_field_type(name)
.expect("no entry for field name")
.to_owned(),
)
self.get_field_type(name)
.expect("no entry for field name")
.to_owned()
})
.collect()
}
Expand All @@ -225,6 +228,10 @@ impl Struct {
pub fn get_field_names(&self) -> Vec<String> {
self.order.clone()
}

pub fn get_num_fields(&self) -> usize {
self.order.len()
}
}

impl TryFrom<&str> for FeString {
Expand Down Expand Up @@ -561,33 +568,31 @@ impl AbiEncoding for Base {

impl FeSized for Array {
fn size(&self) -> usize {
self.dimension * self.inner.size()
self.size * self.inner.size()
}
}

impl AbiEncoding for Array {
fn abi_name(&self) -> String {
if self.inner == Base::Byte {
return format!("bytes{}", self.dimension);
return format!("bytes{}", self.size);
}

format!("{}[{}]", self.inner.abi_name(), self.dimension)
format!("{}[{}]", self.inner.abi_name(), self.size)
}

fn abi_safe_name(&self) -> String {
if self.inner == Base::Byte {
return format!("bytes{}", self.dimension);
return format!("bytes{}", self.size);
}

format!("{}{}", self.inner.abi_name(), self.dimension)
format!("{}{}", self.inner.abi_name(), self.size)
}

fn abi_type(&self) -> AbiType {
AbiType::Array {
inner: Box::new(self.inner.abi_type()),
size: AbiArraySize::Static {
size: self.dimension,
},
size: AbiArraySize::Static { size: self.size },
}
}
}
Expand Down Expand Up @@ -622,15 +627,27 @@ impl FeSized for Struct {

impl AbiEncoding for Struct {
fn abi_name(&self) -> String {
unimplemented!();
let field_names = self
.get_field_types()
.iter()
.map(|typ| typ.abi_name())
.collect::<Vec<String>>();
let joined_names = field_names.join(",");
format!("({})", joined_names)
}

fn abi_safe_name(&self) -> String {
unimplemented!();
self.name.clone()
}

fn abi_type(&self) -> AbiType {
unimplemented!();
AbiType::Tuple {
elems: self
.get_field_types()
.iter()
.map(|typ| typ.abi_type())
.collect(),
}
}
}

Expand Down Expand Up @@ -742,7 +759,7 @@ pub fn type_desc(defs: &HashMap<String, Type>, typ: &fe::TypeDesc) -> Result<Typ
}
fe::TypeDesc::Array { typ, dimension } => Ok(Type::Array(Array {
inner: type_desc_base(defs, &typ.node)?,
dimension: *dimension,
size: *dimension,
})),
fe::TypeDesc::Map { from, to } => Ok(Type::Map(Map {
key: type_desc_base(defs, &from.node)?,
Expand Down
2 changes: 1 addition & 1 deletion analyzer/src/traversal/assignments.rs
Original file line number Diff line number Diff line change
Expand Up @@ -103,7 +103,7 @@ mod tests {
"bar",
FixedSize::Array(Array {
inner: U256,
dimension: 100,
size: 100,
}),
)
.unwrap();
Expand Down
Loading