Dria

Swan
NFTHardhat
21,000 USDC
View results
Submission Details
Severity: medium
Invalid

Missing Fee Validation in Swan.sol Can Lead to Excessive Fee Collection

## Summary

The `Swan` contract lacks proper validation of `royaltyFee` when creating buyer agents and calculating fees in `transferRoyalties`. This oversight allows setting arbitrarily high royalty fees that could exceed 100% of the asset price, potentially leading to excessive fee collection and incorrect fund distribution. ## Vulnerability Details The vulnerability exists in two key areas: 1. **Missing Royalty Fee Validation in Buyer Creation**: ```solidity:Swan.sol function createBuyer( string calldata _name, string calldata _description, uint96 _feeRoyalty, uint256 _amountPerRound ) external returns (BuyerAgent) { // No validation of _feeRoyalty BuyerAgent agent = buyerAgentFactory.deploy(_name, _description, _feeRoyalty, _amountPerRound, msg.sender); emit BuyerCreated(msg.sender, address(agent)); return agent; }

  1. Unsafe Fee Calculations in transferRoyalties:

function transferRoyalties(AssetListing storage asset) internal {
// Unsafe calculations without fee validation
uint256 buyerFee = (asset.price * asset.royaltyFee) / 100;
uint256 driaFee = (buyerFee * getCurrentMarketParameters().platformFee) / 100;
token.transferFrom(asset.seller, address(this), buyerFee);
token.transfer(asset.buyer, buyerFee - driaFee);
token.transfer(owner(), driaFee);
}

Attack Scenario

  1. Attacker creates a buyer agent with royaltyFee = 200 (200%)

  2. For an asset listed at 100 tokens:

    • buyerFee = (100 * 200) / 100 = 200 tokens

    • This already exceeds the original price

  3. Platform fee calculation is then applied to the inflated amount:

    • If platformFee = 10, then driaFee = (200 * 10) / 100 = 20 tokens

  4. Result: Seller pays more in fees than the asset's price

Impact

Severity: High

  1. Financial Impact:

    • Sellers could pay excessive fees exceeding asset prices

    • Incorrect distribution of funds between buyers and platform

    • Potential for economic manipulation of the marketplace

  2. Trust & Usability:

    • Undermines the fairness of the fee system

    • Could deter legitimate sellers from using the platform

    • Reputation damage to the protocol

Tools Used

  • Manual code review

  • Static analysis

  • Mathematical validation of fee calculations

Recommendations

  1. Add Fee Validation in Buyer Creation:

function createBuyer(
string calldata _name,
string calldata _description,
uint96 _feeRoyalty,
uint256 _amountPerRound
) external returns (BuyerAgent) {
require(_feeRoyalty <= 100, "Royalty fee cannot exceed 100%");
require(_feeRoyalty > 0, "Royalty fee must be greater than 0");
BuyerAgent agent = buyerAgentFactory.deploy(
_name,
_description,
_feeRoyalty,
_amountPerRound,
msg.sender
);
emit BuyerCreated(msg.sender, address(agent));
return agent;
}
  1. Add Safety Checks in Fee Calculations:

function transferRoyalties(AssetListing storage asset) internal {
require(asset.royaltyFee <= 100, "Invalid royalty fee");
require(getCurrentMarketParameters().platformFee <= 100, "Invalid platform fee");
uint256 buyerFee = (asset.price * asset.royaltyFee) / 100;
require(buyerFee <= asset.price, "Fee exceeds price");
uint256 driaFee = (buyerFee * getCurrentMarketParameters().platformFee) / 100;
require(driaFee <= buyerFee, "Platform fee exceeds buyer fee");
token.transferFrom(asset.seller, address(this), buyerFee);
token.transfer(asset.buyer, buyerFee - driaFee);
token.transfer(owner(), driaFee);
}
  1. Consider Using Fixed-Point Arithmetic:

    • Implement a fixed-point math library for fee calculations

    • This would provide more precise fee calculations and prevent rounding errors

  2. Add Events for Fee Transfers:

event RoyaltyTransferred(
address indexed asset,
address indexed seller,
address indexed buyer,
uint256 buyerFee,
uint256 platformFee
);
Updates

Lead Judging Commences

inallhonesty Lead Judge 7 months ago
Submission Judgement Published
Invalidated
Reason: Incorrect statement

Support

FAQs

Can't find an answer? Chat with us on Discord, Twitter or Linkedin.