Skip to content
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
35 changes: 5 additions & 30 deletions core/vm/common.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,15 +17,15 @@
package vm

import (
"math/big"
"github.com/core-coin/uint256"

"github.com/core-coin/go-core/common"
"github.com/core-coin/go-core/common/math"
)

// calcMemSize64 calculates the required memory size, and returns
// the size and whether the result overflowed uint64
func calcMemSize64(off, l *big.Int) (uint64, bool) {
func calcMemSize64(off, l *uint256.Int) (uint64, bool) {
if !l.IsUint64() {
return 0, true
}
Expand All @@ -35,16 +35,16 @@ func calcMemSize64(off, l *big.Int) (uint64, bool) {
// calcMemSize64WithUint calculates the required memory size, and returns
// the size and whether the result overflowed uint64
// Identical to calcMemSize64, but length is a uint64
func calcMemSize64WithUint(off *big.Int, length64 uint64) (uint64, bool) {
func calcMemSize64WithUint(off *uint256.Int, length64 uint64) (uint64, bool) {
// if length is zero, memsize is always zero, regardless of offset
if length64 == 0 {
return 0, false
}
// Check that offset doesn't overflow
if !off.IsUint64() {
offset64, overflow := off.Uint64WithOverflow()
if overflow {
return 0, true
}
offset64 := off.Uint64()
val := offset64 + length64
// if value < either of it's parts, then it overflowed
return val, val < offset64
Expand All @@ -64,22 +64,6 @@ func getData(data []byte, start uint64, size uint64) []byte {
return common.RightPadBytes(data[start:end], int(size))
}

// getDataBig returns a slice from the data based on the start and size and pads
// up to size with zero's. This function is overflow safe.
func getDataBig(data []byte, start *big.Int, size *big.Int) []byte {
dlen := big.NewInt(int64(len(data)))

s := math.BigMin(start, dlen)
e := math.BigMin(new(big.Int).Add(s, size), dlen)
return common.RightPadBytes(data[s.Uint64():e.Uint64()], int(size.Uint64()))
}

// bigUint64 returns the integer casted to a uint64 and returns whether it
// overflowed in the process.
func bigUint64(v *big.Int) (uint64, bool) {
return v.Uint64(), !v.IsUint64()
}

// toWordSize returns the ceiled word size required for memory expansion.
func toWordSize(size uint64) uint64 {
if size > math.MaxUint64-31 {
Expand All @@ -88,12 +72,3 @@ func toWordSize(size uint64) uint64 {

return (size + 31) / 32
}

func allZero(b []byte) bool {
for _, byte := range b {
if byte != 0 {
return false
}
}
return true
}
11 changes: 6 additions & 5 deletions core/vm/contract.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
package vm

import (
"github.com/core-coin/uint256"
"math/big"

"github.com/core-coin/go-core/common"
Expand Down Expand Up @@ -57,8 +58,8 @@ type Contract struct {
CodeAddr *common.Address
Input []byte

Energy uint64
value *big.Int
Energy uint64
value *big.Int
}

// NewContract returns a new contract environment for the execution of CVM.
Expand All @@ -81,11 +82,11 @@ func NewContract(caller ContractRef, object ContractRef, value *big.Int, energy
return c
}

func (c *Contract) validJumpdest(dest *big.Int) bool {
udest := dest.Uint64()
func (c *Contract) validJumpdest(dest *uint256.Int) bool {
udest, overflow := dest.Uint64WithOverflow()
// PC cannot go beyond len(code) and certainly can't be bigger than 63bits.
// Don't bother checking for JUMPDEST in that case.
if dest.BitLen() >= 63 || udest >= uint64(len(c.Code)) {
if overflow || udest >= uint64(len(c.Code)) {
return false
}
// Only JUMPDESTs allowed for destinations
Expand Down
6 changes: 3 additions & 3 deletions core/vm/cvm.go
Original file line number Diff line number Diff line change
Expand Up @@ -76,12 +76,12 @@ type Context struct {
GetHash GetHashFunc

// Message information
Origin common.Address // Provides information for ORIGIN
Origin common.Address // Provides information for ORIGIN
EnergyPrice *big.Int // Provides information for ENERGYPRICE

// Block information
Coinbase common.Address // Provides information for COINBASE
EnergyLimit uint64 // Provides information for ENERGYLIMIT
EnergyLimit uint64 // Provides information for ENERGYLIMIT
BlockNumber *big.Int // Provides information for NUMBER
Time *big.Int // Provides information for TIME
Difficulty *big.Int // Provides information for DIFFICULTY
Expand Down Expand Up @@ -338,7 +338,7 @@ func (cvm *CVM) StaticCall(caller ContractRef, addr common.Address, input []byte
// We do an AddBalance of zero here, just in order to trigger a touch.
// but is the correct thing to do and matters on other networks, in tests, and potential
// future scenarios
cvm.StateDB.AddBalance(addr, bigZero)
cvm.StateDB.AddBalance(addr, big.NewInt(0))

// When an error was returned by the CVM or when setting the creation code
// above we revert to the snapshot and consume any energy remaining.
Expand Down
6 changes: 4 additions & 2 deletions core/vm/eips.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,15 +16,17 @@

package vm

import "github.com/core-coin/uint256"

func opSelfBalance(pc *uint64, interpreter *CVMInterpreter, contract *Contract, memory *Memory, stack *Stack) ([]byte, error) {
balance := interpreter.intPool.get().Set(interpreter.cvm.StateDB.GetBalance(contract.Address()))
balance, _ := uint256.FromBig(interpreter.cvm.StateDB.GetBalance(contract.Address()))
stack.push(balance)
return nil, nil
}

// opNetworkID implements NETWORKID opcode
func opNetworkID(pc *uint64, interpreter *CVMInterpreter, contract *Contract, memory *Memory, stack *Stack) ([]byte, error) {
networkId := interpreter.intPool.get().Set(interpreter.cvm.chainConfig.NetworkID)
networkId, _ := uint256.FromBig(interpreter.cvm.chainConfig.NetworkID)
stack.push(networkId)
return nil, nil
}
4 changes: 2 additions & 2 deletions core/vm/energy.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@
package vm

import (
"math/big"
"github.com/core-coin/uint256"
)

// Energy costs
Expand All @@ -33,7 +33,7 @@ const (
// callEnergy returns the actual energy cost of the call.
//
// The returned energy is energy - base * 63 / 64.
func callEnergy(availableEnergy, base uint64, callCost *big.Int) (uint64, error) {
func callEnergy(availableEnergy, base uint64, callCost *uint256.Int) (uint64, error) {
availableEnergy = availableEnergy - base
energy := availableEnergy - availableEnergy/64
// If the bit length exceeds 64 bit we know that the newly calculated "energy" for CIP150
Expand Down
28 changes: 14 additions & 14 deletions core/vm/energy_table.go
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ func memoryCopierEnergy(stackpos int) energyFunc {
return 0, err
}
// And energy for copying data, charged per word at param.CopyEnergy
words, overflow := bigUint64(stack.Back(stackpos))
words, overflow := stack.Back(stackpos).Uint64WithOverflow()
if overflow {
return 0, errEnergyUintOverflow
}
Expand Down Expand Up @@ -114,14 +114,14 @@ func energySStore(cvm *CVM, contract *Contract, stack *Stack, mem *Memory, memor
// Energy sentry honoured, do the actual energy calculation based on the stored value
var (
y, x = stack.Back(1), stack.Back(0)
current = cvm.StateDB.GetState(contract.Address(), common.BigToHash(x))
current = cvm.StateDB.GetState(contract.Address(), common.Hash(x.Bytes32()))
)
value := common.BigToHash(y)
value := common.Hash(y.Bytes32())

if current == value { // noop (1)
return params.SstoreNoopEnergy, nil
}
original := cvm.StateDB.GetCommittedState(contract.Address(), common.BigToHash(x))
original := cvm.StateDB.GetCommittedState(contract.Address(), common.Hash(x.Bytes32()))
if original == current {
if original == (common.Hash{}) { // create slot (2.1.1)
return params.SstoreInitEnergy, nil
Expand Down Expand Up @@ -150,7 +150,7 @@ func energySStore(cvm *CVM, contract *Contract, stack *Stack, mem *Memory, memor

func makeEnergyLog(n uint64) energyFunc {
return func(cvm *CVM, contract *Contract, stack *Stack, mem *Memory, memorySize uint64) (uint64, error) {
requestedSize, overflow := bigUint64(stack.Back(1))
requestedSize, overflow := stack.Back(1).Uint64WithOverflow()
if overflow {
return 0, errEnergyUintOverflow
}
Expand Down Expand Up @@ -183,7 +183,7 @@ func energySha3(cvm *CVM, contract *Contract, stack *Stack, mem *Memory, memoryS
if err != nil {
return 0, err
}
wordEnergy, overflow := bigUint64(stack.Back(1))
wordEnergy, overflow := stack.Back(1).Uint64WithOverflow()
if overflow {
return 0, errEnergyUintOverflow
}
Expand Down Expand Up @@ -217,7 +217,7 @@ func energyCreate2(cvm *CVM, contract *Contract, stack *Stack, mem *Memory, memo
if err != nil {
return 0, err
}
wordEnergy, overflow := bigUint64(stack.Back(2))
wordEnergy, overflow := stack.Back(2).Uint64WithOverflow()
if overflow {
return 0, errEnergyUintOverflow
}
Expand All @@ -234,7 +234,7 @@ func energyExp(cvm *CVM, contract *Contract, stack *Stack, mem *Memory, memorySi
expByteLen := uint64((stack.data[stack.len()-2].BitLen() + 7) / 8)

var (
energy = expByteLen * params.ExpByte // no overflow check required. Max is 256 * ExpByte energy
energy = expByteLen * params.ExpByte // no overflow check required. Max is 256 * ExpByte energy
overflow bool
)
if energy, overflow = math.SafeAdd(energy, params.ExpEnergy); overflow {
Expand All @@ -245,9 +245,9 @@ func energyExp(cvm *CVM, contract *Contract, stack *Stack, mem *Memory, memorySi

func energyCall(cvm *CVM, contract *Contract, stack *Stack, mem *Memory, memorySize uint64) (uint64, error) {
var (
energy uint64
transfersValue = stack.Back(2).Sign() != 0
address = common.BigToAddress(stack.Back(1))
energy uint64
transfersValue = !stack.Back(2).IsZero()
address = common.Address(stack.Back(1).Bytes22())
)
if transfersValue && cvm.StateDB.Empty(address) {
energy += params.CallNewAccountEnergy
Expand All @@ -264,7 +264,7 @@ func energyCall(cvm *CVM, contract *Contract, stack *Stack, mem *Memory, memoryS
return 0, errEnergyUintOverflow
}

cvm.callEnergyTemp, err = callEnergy( contract.Energy, energy, stack.Back(0))
cvm.callEnergyTemp, err = callEnergy(contract.Energy, energy, stack.Back(0))
if err != nil {
return 0, err
}
Expand All @@ -280,7 +280,7 @@ func energyCallCode(cvm *CVM, contract *Contract, stack *Stack, mem *Memory, mem
return 0, err
}
var (
energy uint64
energy uint64
overflow bool
)
if stack.Back(2).Sign() != 0 {
Expand Down Expand Up @@ -335,7 +335,7 @@ func energySelfdestruct(cvm *CVM, contract *Contract, stack *Stack, mem *Memory,
var energy uint64

energy = params.SelfdestructEnergy
var address = common.BigToAddress(stack.Back(0))
var address = common.Address(stack.Back(0).Bytes22())

if cvm.StateDB.Empty(address) && cvm.StateDB.GetBalance(contract.Address()).Sign() != 0 {
energy += params.CreateBySelfdestructEnergy
Expand Down
Loading