-
Notifications
You must be signed in to change notification settings - Fork 20.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Opt opcodes #16939
Opt opcodes #16939
Changes from 3 commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -16,7 +16,12 @@ | |
|
||
package vm | ||
|
||
import "fmt" | ||
import ( | ||
"fmt" | ||
"math/big" | ||
|
||
"github.com/ethereum/go-ethereum/common/math" | ||
) | ||
|
||
// Memory implements a simple memory model for the ethereum virtual machine. | ||
type Memory struct { | ||
|
@@ -43,6 +48,20 @@ func (m *Memory) Set(offset, size uint64, value []byte) { | |
} | ||
} | ||
|
||
// Set32 sets the 32 bytes starting at offset to the value of val, left-padded with zeroes to | ||
// 32 bytes. | ||
func (m *Memory) Set32(offset uint64, val *big.Int) { | ||
// length of store may never be less than offset + size. | ||
// The store should be resized PRIOR to setting the memory | ||
if 32 > uint64(len(m.store)) { | ||
panic("INVALID memory: store empty") | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think the fact you're panicing gets the message across already, no need for the caps :) There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Same as above |
||
} | ||
// Zero the memory area | ||
copy(m.store[offset:offset+32], []byte{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Perhaps use There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Yeah this is me being n00b. I initially attempted There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. For zeroing memory, the compiler recognises loops of the form
Such loops are replaced with a target-specific idiom for clearing memory. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I just tried that:
replace with your loop diff --git a/core/vm/memory.go b/core/vm/memory.go
index a3530419d..9cc7cde40 100644
--- a/core/vm/memory.go
+++ b/core/vm/memory.go
@@ -57,7 +57,10 @@ func (m *Memory) Set32(offset uint64, val *big.Int) {
panic("INVALID memory: store empty")
}
// Zero the memory area
- copy(m.store[offset:offset+32], []byte{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0})
+ for i := range m.store[offset:offset+32] {
+ m.store[offset:offset+32][i] = 0
+ }
+ //copy(m.store[offset:offset+32], []byte{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0})
// Fill in relevant bits
math.ReadBits(val, m.store[offset:offset+32])
}
Another variant diff --git a/core/vm/memory.go b/core/vm/memory.go
index a3530419d..d278f34ae 100644
--- a/core/vm/memory.go
+++ b/core/vm/memory.go
@@ -57,7 +57,10 @@ func (m *Memory) Set32(offset uint64, val *big.Int) {
panic("INVALID memory: store empty")
}
// Zero the memory area
- copy(m.store[offset:offset+32], []byte{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0})
+ for i := range m.store[offset:offset+32] {
+ m.store[i] = 0
+ }
+ //copy(m.store[offset:offset+32], []byte{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0})
// Fill in relevant bits
math.ReadBits(val, m.store[offset:offset+32])
}
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Using a global
|
||
// Fill in relevant bits | ||
math.ReadBits(val, m.store[offset:offset+32]) | ||
} | ||
|
||
// Resize resizes the memory to size | ||
func (m *Memory) Resize(size uint64) { | ||
if uint64(m.Len()) < size { | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You're validating only the size, not the
offset + size
. Shouldn't you haveoffset + 32
here?There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If you expand the code snippet a bit, you'll see that I reused the code above as much as possible, for easier review. I also thought it should be
offset+32
, but it's not in the code above... (?)There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In the snippet above, I believe that if
size
is zero, theoffset
can be arbitrarily high. So checkingsize+offset
for that would be wrong. So whereas in this instance such a check would be ok, this code is no more wrong than the code above. Both depends on resize already having taken place.