Skip to content
This repository has been archived by the owner on Dec 23, 2024. It is now read-only.

feat: add implementation of OpSelfdestruct #29

Merged
merged 1 commit into from
Nov 3, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions fhevm/evm.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import (
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/crypto"
"github.com/holiman/uint256"
ps "github.com/zama-ai/fhevm-go/crypto"
fhevm_crypto "github.com/zama-ai/fhevm-go/crypto"
)

// A Logger interface for the EVM.
Expand Down Expand Up @@ -170,7 +170,7 @@ func padArrayTo32Multiple(input []byte) []byte {

func Create(evm EVMEnvironment, caller common.Address, code []byte, gas uint64, value *big.Int) (ret []byte, contractAddr common.Address, leftOverGas uint64, err error) {
contractAddr = crypto.CreateAddress(caller, evm.GetNonce(caller))
protectedStorageAddr := ps.CreateProtectedStorageContractAddress(contractAddr)
protectedStorageAddr := fhevm_crypto.CreateProtectedStorageContractAddress(contractAddr)
_, _, leftOverGas, err = evm.CreateContract(caller, nil, gas, big.NewInt(0), protectedStorageAddr)
if err != nil {
ret = nil
Expand All @@ -184,7 +184,7 @@ func Create(evm EVMEnvironment, caller common.Address, code []byte, gas uint64,
func Create2(evm EVMEnvironment, caller common.Address, code []byte, gas uint64, endowment *big.Int, salt *uint256.Int) (ret []byte, contractAddr common.Address, leftOverGas uint64, err error) {
codeHash := crypto.Keccak256Hash(code)
contractAddr = crypto.CreateAddress2(caller, salt.Bytes32(), codeHash.Bytes())
protectedStorageAddr := ps.CreateProtectedStorageContractAddress(contractAddr)
protectedStorageAddr := fhevm_crypto.CreateProtectedStorageContractAddress(contractAddr)
_, _, leftOverGas, err = evm.CreateContract2(caller, nil, common.Hash{}, gas, big.NewInt(0), protectedStorageAddr)
if err != nil {
ret = nil
Expand Down
18 changes: 15 additions & 3 deletions fhevm/instructions.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,13 @@ import (
"bytes"
"encoding/hex"
"errors"
"math/big"
"strings"

"github.com/ethereum/go-ethereum/common"
crypto "github.com/ethereum/go-ethereum/crypto"
"github.com/holiman/uint256"
ps "github.com/zama-ai/fhevm-go/crypto"
fhevm_crypto "github.com/zama-ai/fhevm-go/crypto"
)

var zero = uint256.NewInt(0).Bytes32()
Expand Down Expand Up @@ -152,7 +153,7 @@ func verifyIfCiphertextHandle(handle common.Hash, env EVMEnvironment, contractAd
}

metadataKey := crypto.Keccak256Hash(handle.Bytes())
protectedStorage := ps.CreateProtectedStorageContractAddress(contractAddress)
protectedStorage := fhevm_crypto.CreateProtectedStorageContractAddress(contractAddress)
metadataInt := newInt(env.GetState(protectedStorage, metadataKey).Bytes())
if !metadataInt.IsZero() {
metadata := newCiphertextMetadata(metadataInt.Bytes32())
Expand Down Expand Up @@ -274,7 +275,7 @@ func OpSstore(pc *uint64, env EVMEnvironment, scope ScopeContext) ([]byte, error
oldValHash := env.GetState(scope.GetContract().Address(), common.Hash(loc.Bytes32()))
// If the value is the same or if we are not going to commit, don't do anything to protected storage.
if newValHash != oldValHash && env.IsCommitting() {
protectedStorage := ps.CreateProtectedStorageContractAddress(scope.GetContract().Address())
protectedStorage := fhevm_crypto.CreateProtectedStorageContractAddress(scope.GetContract().Address())

// Define flag location as keccak256(keccak256(loc)) in protected storage. Used to mark the location as containing a handle.
// Note: We apply the hash function twice to make sure a flag location in protected storage cannot clash with a ciphertext
Expand Down Expand Up @@ -352,3 +353,14 @@ func OpReturn(pc *uint64, env EVMEnvironment, scope ScopeContext) []byte {
delegateCiphertextHandlesToCaller(env, ret)
return ret
}

func OpSelfdestruct(pc *uint64, env EVMEnvironment, scope ScopeContext) (beneficiary uint256.Int, balance *big.Int) {
beneficiary = scope.GetStack().Pop()
protectedStorage := fhevm_crypto.CreateProtectedStorageContractAddress(scope.GetContract().Address())
balance = env.GetBalance(scope.GetContract().Address())
balance.Add(balance, env.GetBalance(protectedStorage))
env.AddBalance(beneficiary.Bytes20(), balance)
env.Suicide(scope.GetContract().Address())
env.Suicide(protectedStorage)
return
}
4 changes: 4 additions & 0 deletions fhevm/interface.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,10 @@ type EVMEnvironment interface {
GetState(common.Address, common.Hash) common.Hash
SetState(common.Address, common.Hash, common.Hash)
GetNonce(common.Address) uint64
AddBalance(common.Address, *big.Int)
GetBalance(common.Address) *big.Int

Suicide(common.Address) bool

// EVM call stack depth
GetDepth() int
Expand Down