Farseen0/scar-pairs huggingface dataset:
HIGH severity: Missing Access Control for `setDestinationSettler`. The `ERC7683OrderDepositorExternal` contract contains a function `setDestinationSettler` that allows mapping a chain ID to a settler contract address. This mapping is used by the `ERC7683OrderDepositor` contract when constructing fill instructions for cross-chain orders. 
The root cause of the vulne...

Vulnerable code:
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.0;

import "@openzeppelin/contracts/token/ERC20/utils/SafeERC20.sol";
import "@openzeppelin/contracts/access/Ownable.sol";
import { ERC7683OrderDepositor } from "./ERC7683OrderDepositor.sol";
import "../SpokePool.sol";
import "../external/interfaces/IPermit2.sol";
import "@uma/core/contracts/common/implementation/MultiCaller.sol";

/**
 * @notice ERC7683OrderDepositorExternal processes an external order type and translates it into an AcrossV3Deposit
 * that it sends to the SpokePool contract.
 * @custom:security-contact bugs@across.to
 */
contract ERC7683OrderDepositorExternal is ERC7683OrderDepositor, Ownable, MultiCaller {
    using SafeERC20 for IERC20;

    event SetDestinationSettler(
        uint256 indexed chainId,
        address indexed prevDestinationSettler,
        address indexed destinationSettler
    );

    SpokePool public immutable SPOKE_POOL;

    // Mapping of chainIds to destination settler addresses.
    mapping(uint256 => address) public destinationSettlers;

    constructor(
        SpokePool _spokePool,
        IPermit2 _permit2,
        uint256 _quoteBeforeDeadline
    ) ERC7683OrderDepositor(_permit2, _quoteBeforeDeadline) {
        SPOKE_POOL = _spokePool;
    }

    function setDestinationSettler(uint256 chainId, address destinationSettler) external {
        address prevDestinationSettler = destinationSettlers[chainId];
        destinationSettlers[chainId] = destinationSettler;
        emit SetDestinationSettler(chainId, prevDestinationSettler, destinationSettler);
    }

    function _callDeposit(
        address depositor,
        address recipient,
        address inputToken,
        address outputToken,
        uint256 inputAmount,
        uint256 outputAmount,
        uint256 destinationChainId,
        address exclusiveRelayer,
        uint32 quoteTimestamp,
        uint32 fillDeadline,
        uint32 exclusivityDeadline,
        bytes memory message
    ) internal override {
        IERC20(inputToken).safeIncreaseAllowance(address(SPOKE_POOL), inputAmount);

        SPOKE_POOL.depositV3(
            depositor,
            recipient,
            inputToken,
            outputToken,
            inputAmount,
            outputAmount,
            destinationChainId,
            exclusiveRelayer,
            quoteTimestamp,
            fillDeadline,
            exclusivityDeadline,
            message
        );
    }

    function _currentDepositId() internal view override returns (uint32) {
        return SPOKE_POOL.numberOfDeposits();
    }

    function _destinationSettler(uint256 chainId) internal view override returns (address) {
        return destinationSettlers[chainId];
    }
}


Vulnerability type: CWE-284|CWE-285|CWE-862
MEDIUM severity: DisableableAddressWhitelist Is Not Enforced By Default. The DisableableAddressWhitelist contract has an `isEnforced` flag that defaults to false, meaning the whitelist is inactive upon deployment unless explicitly enabled. This creates a risk that the owner may mistakenly believe the whitelist is active, allowing unauthorized addresses to pass checks. Th...

Vulnerable code:
// SPDX-License-Identifier: AGPL-3.0-only
pragma solidity ^0.8.0;

import {AddressWhitelistInterface} from "../interfaces/AddressWhitelistInterface.sol";
import {DisableableAddressWhitelistInterface} from "../interfaces/DisableableAddressWhitelistInterface.sol";
import {AddressWhitelist} from "./AddressWhitelist.sol";

/**
 * @title A contract to track a whitelist of addresses with ability to toggle its enforcement.
 */
contract DisableableAddressWhitelist is AddressWhitelist, DisableableAddressWhitelistInterface {
    bool public isEnforced;

    event WhitelistEnforcementSet(bool enforced);

    /**
     * @notice Disables or enables the whitelist restrictions.
     * @param enforced True to enforce the whitelist, False to disable it.
     */
    function setWhitelistEnforcement(bool enforced) external nonReentrant onlyOwner {
        isEnforced = enforced;
        emit WhitelistEnforcementSet(enforced);
    }

    /**
     * @notice Checks whether an address is on the whitelist and if the whitelist is enabled.
     * @param elementToCheck the address to check.
     * @return True if whitelist enforcement is disabled, or if the address is whitelisted when enforcement is enabled.
     */
    function isOnWhitelist(address elementToCheck)
        public
        view
        override(AddressWhitelist, AddressWhitelistInterface)
        nonReentrantView
        returns (bool)
    {
        return !isEnforced || super.isOnWhitelist(elementToCheck);
    }
}


Vulnerability type: CWE-664|CWE-665|CWE-1419
HIGH severity: PinnedBeaconProxy Can Hide Malicious Implementation via Constructor. The vulnerability allows an attacker to deploy a malicious staking vault implementation by manipulating the constructor of the PinnedBeaconProxy, which is otherwise expected to point to a legitimate implementation. The root cause lies in the fact that the VaultHub validates only the proxy's codehash...

Vulnerable code:
// SPDX-FileCopyrightText: 2025 Lido <info@lido.fi>
// SPDX-License-Identifier: GPL-3.0

// See contracts/COMPILERS.md
pragma solidity 0.8.25;

import {IBeacon} from "@openzeppelin/contracts-v5.2/proxy/beacon/IBeacon.sol";
import {BeaconProxy} from "@openzeppelin/contracts-v5.2/proxy/beacon/BeaconProxy.sol";
import {PinnedBeaconUtils} from "./lib/PinnedBeaconUtils.sol";

/**
 * @title PinnedBeaconProxy
 * @author Lido
 * @notice
 *
 * PinnedBeaconProxy is an extended version of OpenZeppelin's BeaconProxy that adds the ability
 * to "pin" (ossify) specific implementation versions for individual proxy instances.
 *
 * Implementation details:
 * - Uses PinnedBeaconUtils library to manage pinned implementation state
 * - Pinned implementation is stored in a storage slot (keccak256("stakingVault.proxy.pinnedBeacon") - 1)
 * - When ossified, the proxy will always use the pinned implementation instead of the beacon's implementation
 *
 */
contract PinnedBeaconProxy is BeaconProxy {
    constructor(address beacon, bytes memory data) BeaconProxy(beacon, data) payable {}

    function _implementation() internal view virtual override returns (address) {
        address pinnedImpl = PinnedBeaconUtils.getPinnedImplementation();
        if (pinnedImpl != address(0)) {
            return pinnedImpl;
        }
        return IBeacon(_getBeacon()).implementation();
    }

    function implementation() external view returns (address) {
        return _implementation();
    }
}


Vulnerability type: CWE-693|CWE-345|CWE-346
HIGH severity: Vault price manipulation allows yield manager to mint tokens. The yield manager can mint additional tokens when the perceived value of backing assets exceeds the total shares. This vulnerability arises because the _additionalOwnedAssets() function, used to determine asset value, is susceptible to manipulation—such as through an attacker distorting pool prices...

Vulnerable code:
// SPDX-License-Identifier: BUSL-1.1
pragma solidity 0.8.29;

import { Math } from "@openzeppelin/contracts/utils/math/Math.sol";

import { BaseController } from "./BaseController.sol";
import { AccountingLogic } from "./AccountingLogic.sol";

/**
 * @title YieldManager
 * @dev Abstract contract that manages yield distribution for the protocol.
 * Handles the calculation and distribution of yield generated from backing assets,
 * including protocol fee collection and safety buffer management.
 */
abstract contract YieldManager is BaseController, AccountingLogic {
    using Math for uint256;

    /**
     * @dev Role identifier for addresses authorized to distribute yield
     */
    bytes32 public constant YIELD_MANAGER_ROLE = keccak256("YIELD_MANAGER_ROLE");

    /**
     * @dev Emitted when yield is distributed to the yield distributor
     */
    event YieldDistributed(address indexed yieldDistributor, uint256 yield);

    /**
     * @dev Thrown when yield distribution is paused (share redemption price != mint price)
     */
    error Yield_DistributionPaused();
    /**
     * @dev Thrown when the safety buffer exceeds the available yield
     */
    error Yield_ExcessiveSafetyBuffer();

    /**
     * @dev Initializer function for the YieldManager contract
     * @notice This function should be called during contract initialization
     */
    // forge-lint: disable-next-line(mixed-case-function)
    function __YieldManager_init() internal onlyInitializing { }

    /**
     * @notice Distributes yield generated from backing assets to the yield distributor
     * @dev Calculates yield as the difference between backing assets value and share total supply.
     * Deducts safety buffer and protocol fees before distribution.
     * Only callable when share redemption price equals mint price (distribution not paused).
     * @return yield The net amount of yield distributed after fees and safety buffer
     */
    function distributeYield() external nonReentrant onlyRole(YIELD_MANAGER_ROLE) returns (uint256 yield) {
        uint256 value = backingAssetsValue();
        require(_shareRedemptionPrice(value) == SHARE_MINT_PRICE, Yield_DistributionPaused());

        yield = value - _share.totalSupply(); // share redemption price is 1 with same decimals
        require(yield > safetyBufferYieldDeduction, Yield_ExcessiveSafetyBuffer());
        yield -= safetyBufferYieldDeduction;

        _share.mint(address(_yieldDistributor), yield);
        emit YieldDistributed(address(_yieldDistributor), yield);
    }
}


Vulnerability type: CWE-707|CWE-20|CWE-1287
HIGH severity: High Severity: Flashloan Functionality Blocked. 1.  **Description:** A flaw completely blocks the flashloan functionality of the protocol.
2.  **Cause:** The root cause is not detailed in this chunk, but it likely involves a logic error or access control issue in the flashloan execution path.
3.  **Exploitation:** This may not be directly exploit...

Vulnerable code:
// SPDX-License-Identifier: MIT

pragma solidity ^0.8.20;

import { IERC20 } from "@openzeppelin/contracts/token/ERC20/IERC20.sol";
import { SafeERC20 } from "@openzeppelin/contracts/token/ERC20/utils/SafeERC20.sol";

import { IMorphoFlashLoanCallback } from "../../interfaces/Morpho/IMorphoFlashLoanCallback.sol";

import { LibRouter } from "../libraries/LibRouter.sol";

contract MorphoFlashLoanCallbackFacet is IMorphoFlashLoanCallback {
  using SafeERC20 for IERC20;

  /**********
   * Errors *
   **********/

  /// @dev Thrown when the caller is not morpho.
  error ErrorNotFromMorpho();

  error ErrorNotFromRouterFlashLoan();

  /***********************
   * Immutable Variables *
   ***********************/

  /// @dev The address of Morpho Blue contract.
  /// In ethereum, it is 0xbbbbbbbbbb9cc5e90e3b3af64bdaf62c37eeffcb.
  address private immutable morpho;

  /***************
   * Constructor *
   ***************/

  constructor(address _morpho) {
    morpho = _morpho;
  }

  /****************************
   * Public Mutated Functions *
   ****************************/

  /// @inheritdoc IMorphoFlashLoanCallback
  function onMorphoFlashLoan(uint256 assets, bytes calldata data) external {
    if (msg.sender != morpho) revert ErrorNotFromMorpho();

    // make sure call invoked by router
    LibRouter.RouterStorage storage $ = LibRouter.routerStorage();
    if ($.flashLoanContext != LibRouter.HAS_FLASH_LOAN) revert ErrorNotFromRouterFlashLoan();

    (address token, bytes memory realData) = abi.decode(data, (address, bytes));
    (bool success, ) = address(this).call(realData);
    // below lines will propagate inner error up
    if (!success) {
      // solhint-disable-next-line no-inline-assembly
      assembly {
        let ptr := mload(0x40)
        let size := returndatasize()
        returndatacopy(ptr, 0, size)
        revert(ptr, size)
      }
    }

    // flashloan fee is zero in Morpho
    LibRouter.approve(token, msg.sender, assets);
  }
}


Vulnerability type: CWE-703|CWE-755|CWE-248
MEDIUM severity: Participants Are Partially De-Anonymized. The SAMM contract requires the caller to publicly specify the email domain and public key hash of each participant when submitting a proof. While the identity within the domain is hidden, the domain itself is revealed on-chain, reducing the anonymity set to only those participants sharing the same d...

Vulnerable code:
// SPDX-License-Identifier: GPL-3
/**
 *     Safe Anonymization Mail Module
 *     Copyright (C) 2024 OXORIO-FZCO
 *
 *     This program is free software: you can redistribute it and/or modify
 *     it under the terms of the GNU General Public License as published by
 *     the Free Software Foundation, either version 3 of the License, or
 *     (at your option) any later version.
 *
 *     This program is distributed in the hope that it will be useful,
 *     but WITHOUT ANY WARRANTY; without even the implied warranty of
 *     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *     GNU General Public License for more details.
 *
 *     You should have received a copy of the GNU General Public License
 *     along with this program.  If not, see <https://www.gnu.org/licenses/>.
 */
pragma solidity 0.8.23;

import {ISafe} from "../Safe/interfaces/ISafe.sol";
import {ISAMMEvents} from "./ISAMMEvents.sol";
import {ISAMMErrors} from "./ISAMMErrors.sol";
import {ISAMMGetters} from "./ISAMMGetters.sol";

interface ISAMM is ISAMMEvents, ISAMMErrors, ISAMMGetters {
    struct Proof {
        bytes proof;
        uint256 commit;
        string domain;
        bytes32 pubkeyHash;
        bool is2048sig;
    }

    struct TxAllowance {
        address to;
        bytes4 selector;
        uint256 amount;
    }

    function setup(
        address safe,
        uint256 participantsRoot,
        uint64 threshold,
        string calldata relayer,
        address dkimRegistry,
        TxAllowance[] calldata txAllowances
    ) external;

    function executeTransaction(
        address to,
        uint256 value,
        bytes memory data,
        ISafe.Operation operation,
        Proof[] calldata proofs,
        uint256 deadline
    ) external returns (bool success);

    function executeTransactionReturnData(
        address to,
        uint256 value,
        bytes memory data,
        ISafe.Operation operation,
        Proof[] calldata proofs,
        uint256 deadline
    ) external returns (bool success, bytes memory returnData);
}


Vulnerability type: CWE-693|CWE-311|CWE-312
HIGH severity: AFTER_SWAP_RETURNS_DELTA_FLAG isn't turned on. The afterSwap() function is designed to return the protocol swap fee, but the afterSwapReturnDelta flag is not enabled in the hook configuration. As a result, the PoolManager does not parse the return value from afterSwap, treating it as zero and failing to apply the intended fee. This misconfigurat...

Vulnerable code:
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;

import {Hooks} from "v4-core/src/libraries/Hooks.sol";

bool constant POOLS_MUST_HAVE_DYNAMIC_FEE = false;

function getRequiredHookPermissions() pure returns (Hooks.Permissions memory permissions) {
    permissions.beforeInitialize = true; // To constrain that this is an ETH pool

    permissions.afterAddLiquidity = true; // To tax liquidity additions that may be JIT
    permissions.afterAddLiquidityReturnDelta = true; // To charge the JIT liquidity MEV tax.

    permissions.afterRemoveLiquidity = true; // To tax liquidity removals that may be JIT
    permissions.afterRemoveLiquidityReturnDelta = true; // To charge the JIT liquidity MEV tax.

    permissions.beforeSwap = true; // To tax ToB
    permissions.afterSwap = true; // Also to tax with ToB (after swap contains reward dist. calculations)
    permissions.beforeSwapReturnDelta = true; // To charge the ToB MEV tax.
}


Vulnerability type: CWE-693
MEDIUM severity: Zero fee orders are possible if a user performs transactions with a zero gas price. Users can submit valid orders and avoid paying fees if they use a zero gas price.

Vulnerable code:
/*

  Copyright 2018 ZeroEx Intl.

  Licensed under the Apache License, Version 2.0 (the "License");
  you may not use this file except in compliance with the License.
  You may obtain a copy of the License at

    http://www.apache.org/licenses/LICENSE-2.0

  Unless required by applicable law or agreed to in writing, software
  distributed under the License is distributed on an "AS IS" BASIS,
  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  See the License for the specific language governing permissions and
  limitations under the License.

*/

pragma solidity 0.4.25;

contract LibFillResults
{
    struct FillResults {
        uint256 makerAssetFilledAmount;  // Total amount of makerAsset(s) filled.
        uint256 takerAssetFilledAmount;  // Total amount of takerAsset(s) filled.
        uint256 makerFeePaid;            // Total amount of ZRX paid by maker(s) to feeRecipient(s).
        uint256 takerFeePaid;            // Total amount of ZRX paid by taker to feeRecipients(s).
    }

    struct MatchedFillResults {
        FillResults left;                    // Amounts filled and fees paid of left order.
        FillResults right;                   // Amounts filled and fees paid of right order.
        uint256 leftMakerAssetSpreadAmount;  // Spread between price of left and right order, denominated in the left order's makerAsset, paid to taker.
    }
}


Vulnerability type: CWE-284|CWE-285|CWE-862
MEDIUM severity: Untrusted Source. The contract uses an external contract that is untrusted, which may produce security issues and harm transactions.

Vulnerable code:
//SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;

import '@openzeppelin/contracts/token/ERC20/ERC20.sol';
import '@openzeppelin/contracts/access/Ownable.sol';

interface IAntisnipe {
    function assureCanTransfer(
        address sender,
        address from,
        address to,
        uint256 amount
    ) external;
}

contract VirtualVersions is ERC20, Ownable {
    uint256 public totalSupply_ = 1_000_000_000 ether;

    constructor() ERC20('Virtual Versions', 'VV') {
        _mint(msg.sender, totalSupply_);
    }

    IAntisnipe public antisnipe;
    bool public antisnipeDisable;

    function _beforeTokenTransfer(
        address from,
        address to,
        uint256 amount
    ) internal override {
        if (from == address(0) || to == address(0)) return;
        if (!antisnipeDisable && address(antisnipe) != address(0))
            antisnipe.assureCanTransfer(msg.sender, from, to, amount);
    }

    function setAntisnipeDisable() external onlyOwner {
        require(!antisnipeDisable);
        antisnipe = IAntisnipe(address(0));
        antisnipeDisable = true;
    }

    function setAntisnipeAddress(address addr) external onlyOwner {
        antisnipe = IAntisnipe(addr);
    }
}


Vulnerability type: CWE-693|CWE-807
MEDIUM severity: msg.value validation. The swap method does not check msg.value for any transfers (ETH to a token, token to token).

Vulnerable code:
// SPDX-License-Identifier: MIT
pragma solidity ^0.6.2;

interface OneSplitAudit {
    function swap(
        address fromToken,
        address destToken,
        uint256 amount,
        uint256 minReturn,
        uint256[] calldata distribution,
        uint256 flags
    )
        external
        payable
        returns(uint256 returnAmount);

    function getExpectedReturn(
        address fromToken,
        address destToken,
        uint256 amount,
        uint256 parts,
        uint256 flags // See constants in IOneSplit.sol
    )
        external
        view
        returns(
            uint256 returnAmount,
            uint256[] memory distribution
        );
}


Vulnerability type: CWE-20
HIGH severity: MT - Mints Tokens. The contract owner has the authority to mint tokens.

Vulnerable code:
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import "@openzeppelin/contracts/token/ERC20/ERC20.sol";
import "@openzeppelin/contracts/token/ERC20/extensions/ERC20Capped.sol";
import "@openzeppelin/contracts/token/ERC20/extensions/ERC20Burnable.sol";
import "@openzeppelin/contracts/token/ERC20/extensions/draft-ERC20Permit.sol";
import "./TransactionFee.sol";

/**
 * @title Boundless World (BLB) Token
 */
contract BLBToken is ERC20, ERC20Capped, ERC20Burnable, ERC20Permit, TransactionFee {

    constructor(address initialAdmin) 
        ERC20("Boundless World", "BLB") 
        ERC20Capped((3.69 * 10 ** 9) * 10 ** decimals())
        ERC20Permit("Boundless World") 
    {
        _grantRole(DEFAULT_ADMIN_ROLE, initialAdmin);
        _grantRole(MINTER_ROLE, initialAdmin);
        _grantRole(FEE_SETTER_ROLE, initialAdmin);
        _grantRole(FEE_FREE_ROLE, initialAdmin);
    }

    /**
     * Creates amount tokens and assigns them to account, increasing the total supply.
     * 
     * Emits a transfer event with from set to the zero address.
     * 
     * Requirements:
     * 
     * account cannot be the zero address.
     * only role MINTER_ROLE can call this function.
     */
    function mint(address account, uint256 amount) public onlyRole(MINTER_ROLE) {
        _mint(account, amount);
    }

    /**
     * Mint amount of token to every member in accounts.
     * 
     * Emits some transfer events with from set to the zero address to every account.
     * 
     * Requirements:
     * 
     * accounts cannot be the zero address.
     * only role MINTER_ROLE can call this function.
     */
    function mintBatch(
        address[] calldata accounts, 
        uint256 amount
    ) public onlyRole(MINTER_ROLE) {
        for(uint16 i; i < accounts.length; i++){
            _mint(accounts[i], amount);
        }
    }


    // The following functions are overrides required by Solidity.

    function _mint(address to, uint256 amount)
        internal
        override(ERC20, ERC20Capped)
    {
        super._mint(to, amount);
    }

    function _beforeTokenTransfer(address from, address to, uint256 amount)
        internal
        override(ERC20, TransactionFee)
    {
        super._beforeTokenTransfer(from, to, amount);
    }
}

Vulnerability type: CWE-284|CWE-269|CWE-266