Skip to content

Commit

Permalink
restart work on eof
Browse files Browse the repository at this point in the history
  • Loading branch information
racytech committed May 27, 2024
1 parent 504f1f8 commit 3033d4f
Show file tree
Hide file tree
Showing 5 changed files with 51 additions and 12 deletions.
8 changes: 4 additions & 4 deletions core/vm/eips.go
Original file line number Diff line number Diff line change
Expand Up @@ -331,7 +331,7 @@ func enable2935(jt *JumpTable) {

// enableEOF applies the EOF changes.
func enableEOF(jt *JumpTable) {
// Deprecate opcodes
// TODO(racytech): Make sure everything is correct, add all EOF opcodes and remove deprecated ones
undefined := &operation{
execute: opUndefined,
constantGas: 0,
Expand All @@ -344,9 +344,9 @@ func enableEOF(jt *JumpTable) {
jt[JUMP] = undefined
jt[JUMPI] = undefined
jt[PC] = undefined
// JUPMDEST?
// 0x38, 0x39, 0x3b, 0x3c, 0x3f, 0x5a, 0xf1, 0xf2, 0xf4, 0xfa, 0xff - rejected opcodes

// TODO(racytech): Make sure everything is correct
// New opcodes
jt[RJUMP] = &operation{
execute: opRjump,
constantGas: GasQuickStep,
Expand Down Expand Up @@ -374,7 +374,7 @@ func enableEOF(jt *JumpTable) {
}
jt[RETF] = &operation{
execute: opRetf,
constantGas: GasSwiftStep,
constantGas: GasFastestStep,
numPop: 0,
numPush: 0,
terminal: true,
Expand Down
50 changes: 44 additions & 6 deletions core/vm/eof.go
Original file line number Diff line number Diff line change
Expand Up @@ -29,9 +29,10 @@ const (
offsetTypesKind = 3
offsetCodeKind = 6

kindTypes = 1
kindCode = 2
kindData = 3
kindTypes = 1
kindCode = 2
kindContainer = 3
kindData = 4

eofFormatByte = 0xef
eof1Version = 1
Expand Down Expand Up @@ -125,6 +126,8 @@ func (c *Container) MarshalBinary() []byte {

// UnmarshalBinary decodes an EOF container.
func (c *Container) UnmarshalBinary(b []byte) error {
// TODO(racytech): make sure this one is correct!

if !hasEOFMagic(b) {
return fmt.Errorf("%w: want %x", ErrInvalidMagic, eofMagic)
}
Expand All @@ -138,6 +141,7 @@ func (c *Container) UnmarshalBinary(b []byte) error {
var (
kind, typesSize, dataSize int
codeSizes []int
containerSizes []int
err error
)

Expand Down Expand Up @@ -168,8 +172,29 @@ func (c *Container) UnmarshalBinary(b []byte) error {
return fmt.Errorf("%w: mismatch of code sections cound and type signatures, types %d, code %d", ErrInvalidCodeSize, typesSize/4, len(codeSizes))
}

// Parse optional container section here
offsetContainerKind := offsetCodeKind + 2 + 2*len(codeSizes) + 1
if b[offsetContainerKind] == kindContainer { // this if statement makes sure next section is container section
_, containerSizes, err = parseSectionList(b, offsetContainerKind)
if err != nil {
return err
}
if len(containerSizes) == 0 {
return fmt.Errorf("number of container sections may not be 0")
}
if len(containerSizes) > 256 {
return fmt.Errorf("number of container sections must not exceed 256")
}
}

// Parse data section header.
offsetDataKind := offsetCodeKind + 2 + 2*len(codeSizes) + 1
var offsetDataKind int
if len(containerSizes) != 0 { // we have containers, add kind_byte + 2*len(container_sizes) + container_size (2-bytes)
offsetDataKind = offsetContainerKind + 1 + 2*len(containerSizes) + 2
} else {
// no containers
offsetDataKind = offsetContainerKind
}
kind, dataSize, err = parseSection(b, offsetDataKind)
if err != nil {
return err
Expand All @@ -188,7 +213,7 @@ func (c *Container) UnmarshalBinary(b []byte) error {
}

// Verify overall container size.
expectedSize := offsetTerminator + typesSize + sum(codeSizes) + dataSize + 1
expectedSize := offsetTerminator + typesSize + sum(codeSizes) + sum(containerSizes) + dataSize + 1
if len(b) != expectedSize {
return fmt.Errorf("%w: have %d, want %d", ErrInvalidContainerSize, len(b), expectedSize)
}
Expand Down Expand Up @@ -230,6 +255,19 @@ func (c *Container) UnmarshalBinary(b []byte) error {
}
c.Code = code

// Parse containers if any
if len(containerSizes) != 0 {
containers := make([][]byte, len(containerSizes))
for i, size := range containerSizes {
if size == 0 {
return fmt.Errorf("container size may not be 0, container#:%d", i)
}
containers[i] = b[idx : idx+size]
idx += size
}
c.SubContainer = containers
}

// Parse data section.
c.Data = b[idx : idx+dataSize]

Expand Down Expand Up @@ -280,7 +318,7 @@ func parseList(b []byte, idx int) ([]int, error) {
if len(b) <= idx+2+int(count)*2 {
return nil, io.ErrUnexpectedEOF
}
list := make([]int, count)
list := make([]int, count) // list of sizes
for i := 0; i < int(count); i++ {
list[i] = int(binary.BigEndian.Uint16(b[idx+2+2*i:]))
}
Expand Down
1 change: 1 addition & 0 deletions core/vm/evm.go
Original file line number Diff line number Diff line change
Expand Up @@ -380,6 +380,7 @@ func (evm *EVM) create(caller ContractRef, codeAndHash *codeAndHash, gasRemainin
// Validate initcode per EOF rules. If caller is EOF and initcode is legacy, fail.
isInitcodeEOF := hasEOFMagic(codeAndHash.code)
if evm.chainRules.IsPrague {
// TODO(racytech): revisit this part and double check!
if isInitcodeEOF {
// If the initcode is EOF, verify it is well-formed.
var c Container
Expand Down
2 changes: 1 addition & 1 deletion core/vm/interpreter.go
Original file line number Diff line number Diff line change
Expand Up @@ -139,7 +139,7 @@ func NewEVMInterpreter(evm *EVM, cfg Config) *EVMInterpreter {
switch {
case evm.ChainRules().IsPrague:
jt = &pragueInstructionSet
eofJt = &pragueInstructionSet
eofJt = &pragueEOFInstructionSet
case evm.ChainRules().IsCancun:
jt = &cancunInstructionSet
case evm.ChainRules().IsNapoli:
Expand Down
2 changes: 1 addition & 1 deletion core/vm/opcodes.go
Original file line number Diff line number Diff line change
Expand Up @@ -219,7 +219,7 @@ const (
DATALOADN OpCode = 0xe9
DATASIZE OpCode = 0xea
DATACOPY OpCode = 0xeb
CREATE3 OpCode = 0xec
CREATE3 OpCode = 0xec // TODO(racytech): remove CREATE3 and CREATE4, add EOFCREATE instead
CREATE4 OpCode = 0xed
RETURNCONTRACT OpCode = 0xee
)
Expand Down

0 comments on commit 3033d4f

Please sign in to comment.