Skip to content

Commit

Permalink
add Reentrancy Locks test contract add update StorageContract.sol (#851)
Browse files Browse the repository at this point in the history
Co-authored-by: Kyon <32325790+kyonRay@users.noreply.github.com>
  • Loading branch information
wenlinlee and kyonRay authored Jul 29, 2024
1 parent 19f3cbd commit 6076299
Show file tree
Hide file tree
Showing 4 changed files with 101 additions and 4 deletions.
13 changes: 9 additions & 4 deletions .github/workflows/workflow.yml
Original file line number Diff line number Diff line change
Expand Up @@ -44,14 +44,19 @@ jobs:
strategy:
fail-fast: false
matrix:
os: [ubuntu-20.04]
container: docker.io/centos:7
os: [ ubuntu-20.04 ]
container: docker.io/centos:latest
steps:
- uses: actions/checkout@v2
with:
fetch-depth: 5
- name: install CentOS dependencies
run: yum install -y epel-release centos-release-scl which git openssl-devel openssl wget
run: |
cd /etc/yum.repos.d/
sed -i 's/mirrorlist/#mirrorlist/g' /etc/yum.repos.d/CentOS-*
sed -i 's|#baseurl=http://mirror.centos.org|baseurl=http://vault.centos.org|g' /etc/yum.repos.d/CentOS-*
yum update -y
yum install -y which git openssl-devel openssl wget
- name: Set up JDK 1.8
uses: actions/setup-java@v3
with:
Expand All @@ -60,4 +65,4 @@ jobs:
- name: run integration testing
run: /bin/bash -x .ci/ci_check.sh
- name: upload coverage
run: curl -LO https://codecov.io/bash && /bin/bash ./bash
run: curl -LO https://codecov.io/bash && /bin/bash ./bash
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
contract DoubleBufferContract {
uint[] bufferA;
uint[] bufferB;

modifier nonreentrant(bytes32 key) {
assembly {
if tload(key) {revert(0, 0)}
tstore(key, 1)
}
_;
assembly {
tstore(key, 0)
}
}

bytes32 constant A_LOCK = keccak256("a");
bytes32 constant B_LOCK = keccak256("b");

function pushA() nonreentrant(A_LOCK) public payable {
bufferA.push(msg.value);
}

function popA() nonreentrant(A_LOCK) public {
require(bufferA.length > 0);

(bool success,) = msg.sender.call{value: bufferA[bufferA.length - 1]}("");
require(success);
bufferA.pop();
}

function pushB() nonreentrant(B_LOCK) public payable {
bufferB.push(msg.value);
}

function popB() nonreentrant(B_LOCK) public {
require(bufferB.length > 0);

(bool success,) = msg.sender.call{value: bufferB[bufferB.length - 1]}("");
require(success);
bufferB.pop();
}

function getBufferA() public view returns (uint256[] memory) {
return bufferA;
}

function getBufferB() public view returns (uint256[] memory) {
return bufferB;
}
}
15 changes: 15 additions & 0 deletions src/main/resources/contract/solidity/0.8.26/StorageContract.sol
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ contract StorageContract {
StorageSlot.Int256SlotType private int256Slot = StorageSlot.asInt256(keccak256("int256_slot"));

function setAddress(address _value) public {
require(_value != address(0), "Invalid address");
addressSlot.tstore(_value);
}

Expand All @@ -20,6 +21,8 @@ contract StorageContract {
}

function setBoolean(bool _value) public {
require(_value == true, "Input must be a boolean value");
require(_value == false, "Input must be a boolean value");
booleanSlot.tstore(_value);
}

Expand All @@ -28,6 +31,7 @@ contract StorageContract {
}

function setBytes32(bytes32 _value) public {
require(_value != bytes32(0), "Invalid bytes32 value");
bytes32Slot.tstore(_value);
}

Expand All @@ -36,6 +40,7 @@ contract StorageContract {
}

function setUint256(uint256 _value) public {
require(_value <= type(uint256).max, "Invalid uint256 value");
uint256Slot.tstore(_value);
}

Expand All @@ -44,6 +49,8 @@ contract StorageContract {
}

function setInt256(int256 _value) public {
require(_value >= type(int256).min, "Invalid int256 value");
require(_value < type(int256).max, "Invalid int256 value");
int256Slot.tstore(_value);
}

Expand All @@ -52,26 +59,34 @@ contract StorageContract {
}

function storeIntTest(int256 _value) public returns (int256) {
require(_value >= type(int256).min, "Invalid int256 value");
require(_value < type(int256).max, "Invalid int256 value");
int256Slot.tstore(_value);

return int256Slot.tload();
}

function storeUintTest(uint256 _value) public returns (uint256) {
require(_value <= type(uint256).max, "Invalid uint256 value");
uint256Slot.tstore(_value);
return uint256Slot.tload();
}

function storeBytes32Test(bytes32 _value) public returns (bytes32) {
require(_value != bytes32(0), "Invalid bytes32 value");
bytes32Slot.tstore(_value);
return bytes32Slot.tload();
}

function storeBooleanTest(bool _value) public returns (bool) {
require(_value == true, "Input must be a boolean value");
require(_value == false, "Input must be a boolean value");
booleanSlot.tstore(_value);
return booleanSlot.tload();
}

function storeAddressTest(address _value) public returns (address) {
require(_value != address(0), "Invalid address");
addressSlot.tstore(_value);
return addressSlot.tload();
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
pragma solidity ^0.8.0;

import "./DoubleBufferContract.sol";

contract TestDoubleBufferContract {
DoubleBufferContract public doubleBufferContract;

constructor() {
doubleBufferContract = new DoubleBufferContract();
}

function testReentrancyA() public {
doubleBufferContract.pushA{value: 1 ether}();
// 尝试再次调用pushA函数,应该被阻止
doubleBufferContract.pushA{value: 1 ether}();
}

function testReentrancyB() public {
doubleBufferContract.pushB{value: 1 ether}();
// 尝试再次调用pushB函数,应该被阻止
doubleBufferContract.pushB{value: 1 ether}();
}

receive() external payable {
doubleBufferContract.pushA{value: 1 ether}();
}
}

0 comments on commit 6076299

Please sign in to comment.