TempleGold

TempleDAO
Foundry
25,000 USDC
View results
Submission Details
Severity: low
Invalid

There is no check if the provided fees are enough to cover the execution of some transactions

Summary

The LayerZero requires a certain amount of fees to be provided in order to successfully execute the transaction. But some functions don't check if a sufficient amount of fee has been provided.

Vulnerability Details

In LayerZero, the destination chain's function call requires a specific gas amount. If the desired gas amount is not provided, it will revert with an out-of-gas exception. The TempleGold::send function relies on the responsibility of the user to ensure that appropriate fees are established.

function send(
SendParam calldata _sendParam,
MessagingFee calldata _fee,
address _refundAddress
) external payable virtual override(IOFT, OFTCore) returns (MessagingReceipt memory msgReceipt, OFTReceipt memory oftReceipt) {
if (_sendParam.composeMsg.length > 0) { revert CannotCompose(); }
/// cast bytes32 to address
address _to = _sendParam.to.bytes32ToAddress();
/// @dev user can cross-chain transfer to self
if (msg.sender != _to) { revert ITempleGold.NonTransferrable(msg.sender, _to); }
// @dev Applies the token transfers regarding this send() operation.
// - amountSentLD is the amount in local decimals that was ACTUALLY sent/debited from the sender.
// - amountReceivedLD is the amount in local decimals that will be received/credited to the recipient on the remote OFT instance.
(uint256 amountSentLD, uint256 amountReceivedLD) = _debit(
msg.sender,
_sendParam.amountLD,
_sendParam.minAmountLD,
_sendParam.dstEid
);
// @dev Builds the options and OFT message to quote in the endpoint.
(bytes memory message, bytes memory options) = _buildMsgAndOptions(_sendParam, amountReceivedLD);
// @dev Sends the message to the LayerZero endpoint and returns the LayerZero msg receipt.
msgReceipt = _lzSend(_sendParam.dstEid, message, options, _fee, _refundAddress);
// @dev Formulate the OFT receipt.
oftReceipt = OFTReceipt(amountSentLD, amountReceivedLD);
emit OFTSent(msgReceipt.guid, _sendParam.dstEid, msg.sender, amountSentLD, amountReceivedLD);
}

There is a function TempleTeleporter::quote that the user can call to calculate the fee. But actually the user can pass arbitrary value for the fee in the TempleGold::send function. There is no check in the function that ensures the user has provided the sufficient amount for the fee for properly execution of the send function.

There is the same problem in TempleTeleporter::teleport function:

function teleport(
uint32 dstEid,
address to,
uint256 amount,
bytes calldata options
) external payable override returns(MessagingReceipt memory receipt) {
if (amount == 0) { revert CommonEventsAndErrors.ExpectedNonZero(); }
if (to == address(0)) { revert CommonEventsAndErrors.InvalidAddress(); }
// Encodes the message before invoking _lzSend.
bytes memory _payload = abi.encodePacked(to.addressToBytes32(), amount);
// debit
temple.burnFrom(msg.sender, amount);
emit TempleTeleported(dstEid, msg.sender, to, amount);
receipt = _lzSend(dstEid, _payload, options, MessagingFee(msg.value, 0), payable(msg.sender));
}

The function requires enough msg.value to be sent to cover completing execution and the transfer by endpoint and on the destination chain. But the function doesn't check if enough msg.value is actually send. It relies on the responsibility of the user.

Impact

The malicious user can constantly call the TempleGold::send or TempleTeleporter::teleport function with a small amount of fee and the functions will always revert due to out of gas error. In that way the attacker can block the communication between the source and the destination chain.

Tools Used

Manual Review

Recommendations

Add a check to ensure that the user has provided the minimum amount value for the fee.

Updates

Lead Judging Commences

inallhonesty Lead Judge
about 1 year ago
inallhonesty Lead Judge about 1 year ago
Submission Judgement Published
Invalidated
Reason: Non-acceptable severity
Assigned finding tags:

Fee validation issue in send

Support

FAQs

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