Gas

契約呼叫中的氣體不足問題

  • December 26, 2020

這里乙太掃描連結到失敗的交易:

合約呼叫陷入 gas 錯誤。它基本上是一個呼叫另一個呼叫的合約鏈。當我們深入研究這個問題時,我們已經看到它在下面的方法中失敗了。

Launchpad.sol 去簽約

   /**
   * @dev Function to setup liquidity and transfer all amounts according to defined percents, if softcap not reached set Refunded flag.
   */
   function setupLiquidity() public onlyOwner {
       require(_isSoldOut == true || block.timestamp > _end , "LaunchpadToken: not sold out or time not elapsed yet" );
       require(_isRefunded == false, "Launchpad: refunded is activated");
       require(_isLiquiditySetup == false, "Setup has already been completed");
       _isLiquiditySetup = true;
       if(_raisedETH < _softCap){
           _isRefunded = true;
           return;
       }
       uint256 ethBalance = address(this).balance;
       require(ethBalance > 0, "LaunchpadToken: eth balance needs to be above zero" );
       uint256 liquidityAmount = ethBalance.mul(_liquidityPercent).div(_totalPercent);
       uint256 tokensAmount = _token.balanceOf(address(this));
       require(tokensAmount >= liquidityAmount.mul(_BASE_PRICE).div(_priceUniInv), "Launchpad: Not sufficient tokens amount");
       uint256 teamAmount = ethBalance.mul(_teamPercent).div(_totalPercent);
       uint256 layerFeeAmount = ethBalance.mul(_fee3).div(_totalPercent);
       uint256 supportFeeAmount = ethBalance.mul(_fee1).div(_totalPercent);
       uint256 stakeFeeAmount = ethBalance.mul(_fee1).div(_totalPercent);
       payable(_layerFeeAddress).transfer(layerFeeAmount);
       payable(_supportFeeAddress).transfer(supportFeeAmount);
       payable(_stakeFeeAddress).transfer(stakeFeeAmount);
       payable(_teamWallet).transfer(teamAmount);
       payable(_liquidityCreator).transfer(liquidityAmount);
       _token.safeTransfer(address(_liquidityCreator), liquidityAmount.mul(_BASE_PRICE).div(_priceUniInv));
   }

不知何故,它可以在測試網上執行;但在主網上失敗。

  • 測試網合約:連結
  • 帶有setupLiquidity()呼叫的測試網成功交易。關聯

理論是;

  • 鍊式合約呼叫有更高的 gas 限制要求,迄今為止的最高嘗試是 666,666 gas 限制,但仍然失敗。可能是許多投資者造成了這種情況,因為在測試網上很少存在。如果是這種情況,我們如何估算所需的氣體限制?
  • 合約觸發交易使用 2300 gas,無論發起者交易有多少 gas 限制。這看起來也很奇怪。

契約:

問題是 Launchpad 使用 .transfer 將乙太幣傳輸到 Layerx,因此接收器有 2300 的氣體津貼

payable(_stakeFeeAddress).transfer(stakeFeeAmount);

由於 Layerx 備份修改了儲存,它需要超過 2300 的儲存空間,並且導致 setupLiquidity 恢復時出現氣體不足錯誤

function() external payable {
   ethToNextStake = ethToNextStake.add(msg.value); 
}

引用自:https://ethereum.stackexchange.com/questions/91525