Skip to content

Commit

Permalink
Merge branch 'dev' into dev-pyth-deprecated-functions
Browse files Browse the repository at this point in the history
  • Loading branch information
montyly authored Oct 10, 2024
2 parents bae46ba + 8190a48 commit 25f6e46
Show file tree
Hide file tree
Showing 6 changed files with 129 additions and 0 deletions.
1 change: 1 addition & 0 deletions slither/detectors/all_detectors.py
Original file line number Diff line number Diff line change
Expand Up @@ -98,5 +98,6 @@
from .statements.return_bomb import ReturnBomb
from .functions.out_of_order_retryable import OutOfOrderRetryable
from .functions.pyth_deprecated_functions import PythDeprecatedFunctions
from .functions.optimism_deprecation import OptimismDeprecation

# from .statements.unused_import import UnusedImport
92 changes: 92 additions & 0 deletions slither/detectors/functions/optimism_deprecation.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
from typing import List

from slither.detectors.abstract_detector import (
AbstractDetector,
DetectorClassification,
DETECTOR_INFO,
)
from slither.core.cfg.node import Node
from slither.core.variables.variable import Variable
from slither.core.expressions import TypeConversion, Literal
from slither.utils.output import Output


class OptimismDeprecation(AbstractDetector):

ARGUMENT = "optimism-deprecation"
HELP = "Detect when deprecated Optimism predeploy or function is used."
IMPACT = DetectorClassification.LOW
CONFIDENCE = DetectorClassification.HIGH

WIKI = "https://github.com/crytic/slither/wiki/Detector-Documentation#optimism-deprecation"

WIKI_TITLE = "Optimism deprecated predeploy or function"
WIKI_DESCRIPTION = "Detect when deprecated Optimism predeploy or function is used."

# region wiki_exploit_scenario
WIKI_EXPLOIT_SCENARIO = """
```solidity
interface GasPriceOracle {
function scalar() external view returns (uint256);
}
contract Test {
GasPriceOracle constant OPT_GAS = GasPriceOracle(0x420000000000000000000000000000000000000F);
function a() public {
OPT_GAS.scalar();
}
}
```
The call to the `scalar` function of the Optimism GasPriceOracle predeploy always revert.
"""
# endregion wiki_exploit_scenario

WIKI_RECOMMENDATION = "Do not use the deprecated components."

def _detect(self) -> List[Output]:
results = []

deprecated_predeploys = [
"0x4200000000000000000000000000000000000000", # LegacyMessagePasser
"0x4200000000000000000000000000000000000001", # L1MessageSender
"0x4200000000000000000000000000000000000002", # DeployerWhitelist
"0x4200000000000000000000000000000000000013", # L1BlockNumber
]

for contract in self.compilation_unit.contracts_derived:
use_deprecated: List[Node] = []

for _, ir in contract.all_high_level_calls:
# To avoid FPs we assume predeploy contracts are always assigned to a constant and typecasted to an interface
# and we check the target address of a high level call.
if (
isinstance(ir.destination, Variable)
and isinstance(ir.destination.expression, TypeConversion)
and isinstance(ir.destination.expression.expression, Literal)
):
if ir.destination.expression.expression.value in deprecated_predeploys:
use_deprecated.append(ir.node)

if (
ir.destination.expression.expression.value
== "0x420000000000000000000000000000000000000F"
and ir.function_name in ("overhead", "scalar", "getL1GasUsed")
):
use_deprecated.append(ir.node)
# Sort so output is deterministic
use_deprecated.sort(key=lambda x: (x.node_id, x.function.full_name))
if len(use_deprecated) > 0:
info: DETECTOR_INFO = [
"A deprecated Optimism predeploy or function is used in the ",
contract.name,
" contract.\n",
]

for node in use_deprecated:
info.extend(["\t - ", node, "\n"])

res = self.generate_result(info)
results.append(res)

return results
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
A deprecated Optimism predeploy or function is used in the Test contract.
- OPT_GAS.scalar() (tests/e2e/detectors/test_data/optimism-deprecation/0.8.20/optimism_deprecation.sol#15)
- L1_BLOCK_NUMBER.q() (tests/e2e/detectors/test_data/optimism-deprecation/0.8.20/optimism_deprecation.sol#19)

Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
interface GasPriceOracle {
function scalar() external view returns (uint256);
function baseFee() external view returns (uint256);
}

interface L1BlockNumber {
function q() external view returns (uint256);
}

contract Test {
GasPriceOracle constant OPT_GAS = GasPriceOracle(0x420000000000000000000000000000000000000F);
L1BlockNumber constant L1_BLOCK_NUMBER = L1BlockNumber(0x4200000000000000000000000000000000000013);

function bad() public {
OPT_GAS.scalar();
}

function bad2() public {
L1_BLOCK_NUMBER.q();
}

function good() public {
OPT_GAS.baseFee();
}


}
Binary file not shown.
5 changes: 5 additions & 0 deletions tests/e2e/detectors/test_detectors.py
Original file line number Diff line number Diff line change
Expand Up @@ -1719,6 +1719,11 @@ def id_test(test_item: Test):
"pyth_deprecated_functions.sol",
"0.8.20",
),
Test(
all_detectors.OptimismDeprecation,
"optimism_deprecation.sol",
"0.8.20",
),
# Test(
# all_detectors.UnusedImport,
# "ConstantContractLevelUsedInContractTest.sol",
Expand Down

0 comments on commit 25f6e46

Please sign in to comment.