Skip to content

Commit

Permalink
fix(syn-solidity): allow some duplicate attributes (#399)
Browse files Browse the repository at this point in the history
  • Loading branch information
DaniPopes authored Nov 3, 2023
1 parent 9877bb2 commit 477227d
Show file tree
Hide file tree
Showing 2 changed files with 49 additions and 27 deletions.
37 changes: 37 additions & 0 deletions crates/sol-types/tests/sol.rs
Original file line number Diff line number Diff line change
Expand Up @@ -572,6 +572,43 @@ fn event_tokenize_fields() {
};
}

// Allow multiple overrides of the same function
// https://github.com/alloy-rs/core/issues/398
#[test]
fn duplicate_attributes() {
sol! {
contract TaxableTeamToken is IERC20, Context, Ownable {
constructor(
string memory name,
string memory symbol,
uint8 decimals,
uint256 supply,
uint256 fees,
address owner,
address feeWallet
) public checkIsFeesValid(fees) checkIsFeesValid(fees2) checkIsAddressValid(owner) checkIsAddressValid(feeWallet) {
require(decimals >=8 && decimals <= 18, "[Validation] Not valid decimals");
require(supply > 0, "[Validation] inital supply should be greater than 0");
require(owner != feeWallet, "[Validation] fee wallet and owner wallet cannot be same.");

_name = name;
_symbol = symbol;
_decimals = decimals;
_feesPercentage = fees;

_tTotal = supply;
_rTotal = (MAX - (MAX % _tTotal));

_rOwned[owner] = _rTotal;

emit Transfer(address(0), owner, _tTotal);

emit TeamFinanceTokenMint(owner);
}
}
}
}

#[test]
#[cfg(feature = "json")]
fn abigen_json_large_array() {
Expand Down
39 changes: 12 additions & 27 deletions crates/syn-solidity/src/attribute/function.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,6 @@ use crate::{kw, Modifier, Mutability, Override, SolPath, Spanned, VariableAttrib
use proc_macro2::Span;
use std::{
fmt,
hash::{Hash, Hasher},
mem,
ops::{Deref, DerefMut},
};
use syn::{
Expand Down Expand Up @@ -55,10 +53,17 @@ impl Parse for FunctionAttributes {
let mut attributes = Vec::<FunctionAttribute>::new();
while !input.is_empty() && !input.peek(kw::returns) && input.peek(Ident::peek_any) {
let attr: FunctionAttribute = input.parse()?;
if let Some(prev) = attributes.iter().find(|a| **a == attr) {
let mut e = Error::new(attr.span(), "duplicate attribute");
e.combine(Error::new(prev.span(), "previous declaration is here"));
return Err(e)
if matches!(
attr,
FunctionAttribute::Visibility(_)
| FunctionAttribute::Mutability(_)
| FunctionAttribute::Virtual(_)
) {
if let Some(prev) = attributes.iter().find(|a| **a == attr) {
let mut e = Error::new(attr.span(), "duplicate attribute");
e.combine(Error::new(prev.span(), "previous declaration is here"));
return Err(e)
}
}
attributes.push(attr);
}
Expand Down Expand Up @@ -128,7 +133,7 @@ impl FunctionAttributes {
}

/// A function attribute.
#[derive(Clone)]
#[derive(Clone, PartialEq, Eq, Hash)]
pub enum FunctionAttribute {
/// A [Visibility] attribute.
Visibility(Visibility),
Expand Down Expand Up @@ -166,26 +171,6 @@ impl fmt::Debug for FunctionAttribute {
}
}

impl PartialEq for FunctionAttribute {
fn eq(&self, other: &Self) -> bool {
match (self, other) {
(Self::Modifier(a), Self::Modifier(b)) => a == b,
_ => mem::discriminant(self) == mem::discriminant(other),
}
}
}

impl Eq for FunctionAttribute {}

impl Hash for FunctionAttribute {
fn hash<H: Hasher>(&self, state: &mut H) {
mem::discriminant(self).hash(state);
if let Self::Modifier(m) = self {
m.hash(state);
}
}
}

impl Parse for FunctionAttribute {
fn parse(input: ParseStream<'_>) -> Result<Self> {
let lookahead = input.lookahead1();
Expand Down

0 comments on commit 477227d

Please sign in to comment.