Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
G
Geth-Modification
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
张蕾
Geth-Modification
Commits
a96c8c8a
Commit
a96c8c8a
authored
Apr 18, 2014
by
obscuren
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Added proper gas handling
parent
c5729d7e
Changes
5
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
26 additions
and
20 deletions
+26
-20
closure.go
ethchain/closure.go
+3
-2
state_manager.go
ethchain/state_manager.go
+2
-1
transaction.go
ethchain/transaction.go
+6
-6
vm.go
ethchain/vm.go
+5
-4
vm_test.go
ethchain/vm_test.go
+10
-7
No files found.
ethchain/closure.go
View file @
a96c8c8a
...
...
@@ -27,14 +27,15 @@ type Closure struct {
State
*
State
Gas
*
big
.
Int
Price
*
big
.
Int
Value
*
big
.
Int
Args
[]
byte
}
// Create a new closure for the given data items
func
NewClosure
(
callee
Callee
,
object
Reference
,
script
[]
byte
,
state
*
State
,
gas
,
val
*
big
.
Int
)
*
Closure
{
return
&
Closure
{
callee
,
object
,
script
,
state
,
gas
,
val
,
nil
}
func
NewClosure
(
callee
Callee
,
object
Reference
,
script
[]
byte
,
state
*
State
,
gas
,
price
,
val
*
big
.
Int
)
*
Closure
{
return
&
Closure
{
callee
,
object
,
script
,
state
,
gas
,
price
,
val
,
nil
}
}
// Retuns the x element in data slice
...
...
ethchain/state_manager.go
View file @
a96c8c8a
...
...
@@ -310,7 +310,7 @@ func (sm *StateManager) EvalScript(script []byte, object *StateObject, tx *Trans
}()
caller
:=
sm
.
procState
.
GetAccount
(
tx
.
Sender
())
closure
:=
NewClosure
(
caller
,
object
,
script
,
sm
.
procState
,
tx
.
Gas
,
tx
.
Value
)
closure
:=
NewClosure
(
caller
,
object
,
script
,
sm
.
procState
,
tx
.
Gas
,
tx
.
GasPrice
,
tx
.
Value
)
vm
:=
NewVm
(
sm
.
procState
,
RuntimeVars
{
Origin
:
caller
.
Address
(),
BlockNumber
:
block
.
BlockInfo
()
.
Number
,
...
...
@@ -318,6 +318,7 @@ func (sm *StateManager) EvalScript(script []byte, object *StateObject, tx *Trans
Coinbase
:
block
.
Coinbase
,
Time
:
block
.
Time
,
Diff
:
block
.
Difficulty
,
//Price: tx.GasPrice,
})
closure
.
Call
(
vm
,
nil
,
nil
)
...
...
ethchain/transaction.go
View file @
a96c8c8a
...
...
@@ -13,7 +13,7 @@ type Transaction struct {
Recipient
[]
byte
Value
*
big
.
Int
Gas
*
big
.
Int
Gas
p
rice
*
big
.
Int
Gas
P
rice
*
big
.
Int
Data
[]
byte
Init
[]
byte
v
byte
...
...
@@ -24,11 +24,11 @@ type Transaction struct {
}
func
NewContractCreationTx
(
value
,
gasprice
*
big
.
Int
,
script
[]
byte
,
init
[]
byte
)
*
Transaction
{
return
&
Transaction
{
Value
:
value
,
Gas
p
rice
:
gasprice
,
Data
:
script
,
Init
:
init
,
contractCreation
:
true
}
return
&
Transaction
{
Value
:
value
,
Gas
P
rice
:
gasprice
,
Data
:
script
,
Init
:
init
,
contractCreation
:
true
}
}
func
NewTransactionMessage
(
to
[]
byte
,
value
,
gasprice
,
gas
*
big
.
Int
,
data
[]
byte
)
*
Transaction
{
return
&
Transaction
{
Recipient
:
to
,
Value
:
value
,
Gas
p
rice
:
gasprice
,
Gas
:
gas
,
Data
:
data
}
return
&
Transaction
{
Recipient
:
to
,
Value
:
value
,
Gas
P
rice
:
gasprice
,
Gas
:
gas
,
Data
:
data
}
}
func
NewTransactionFromBytes
(
data
[]
byte
)
*
Transaction
{
...
...
@@ -46,7 +46,7 @@ func NewTransactionFromValue(val *ethutil.Value) *Transaction {
}
func
(
tx
*
Transaction
)
Hash
()
[]
byte
{
data
:=
[]
interface
{}{
tx
.
Nonce
,
tx
.
Value
,
tx
.
Gas
p
rice
,
tx
.
Gas
,
tx
.
Recipient
,
string
(
tx
.
Data
)}
data
:=
[]
interface
{}{
tx
.
Nonce
,
tx
.
Value
,
tx
.
Gas
P
rice
,
tx
.
Gas
,
tx
.
Recipient
,
string
(
tx
.
Data
)}
if
tx
.
contractCreation
{
data
=
append
(
data
,
string
(
tx
.
Init
))
}
...
...
@@ -107,7 +107,7 @@ func (tx *Transaction) Sign(privk []byte) error {
// [ NONCE, VALUE, GASPRICE, GAS, TO, DATA, V, R, S ]
// [ NONCE, VALUE, GASPRICE, GAS, 0, CODE, INIT, V, R, S ]
func
(
tx
*
Transaction
)
RlpData
()
interface
{}
{
data
:=
[]
interface
{}{
tx
.
Nonce
,
tx
.
Value
,
tx
.
Gas
p
rice
,
tx
.
Gas
,
tx
.
Recipient
,
tx
.
Data
}
data
:=
[]
interface
{}{
tx
.
Nonce
,
tx
.
Value
,
tx
.
Gas
P
rice
,
tx
.
Gas
,
tx
.
Recipient
,
tx
.
Data
}
if
tx
.
contractCreation
{
data
=
append
(
data
,
tx
.
Init
)
...
...
@@ -132,7 +132,7 @@ func (tx *Transaction) RlpDecode(data []byte) {
func
(
tx
*
Transaction
)
RlpValueDecode
(
decoder
*
ethutil
.
Value
)
{
tx
.
Nonce
=
decoder
.
Get
(
0
)
.
Uint
()
tx
.
Value
=
decoder
.
Get
(
1
)
.
BigInt
()
tx
.
Gas
p
rice
=
decoder
.
Get
(
2
)
.
BigInt
()
tx
.
Gas
P
rice
=
decoder
.
Get
(
2
)
.
BigInt
()
tx
.
Gas
=
decoder
.
Get
(
3
)
.
BigInt
()
tx
.
Recipient
=
decoder
.
Get
(
4
)
.
Bytes
()
tx
.
Data
=
decoder
.
Get
(
5
)
.
Bytes
()
...
...
ethchain/vm.go
View file @
a96c8c8a
...
...
@@ -71,7 +71,7 @@ func (vm *Vm) RunClosure(closure *Closure, hook DebugHook) (ret []byte, err erro
// New stack (should this be shared?)
stack
:=
NewStack
()
require
:=
func
(
m
int
)
{
if
stack
.
Len
()
-
1
>
m
{
if
stack
.
Len
()
<
m
{
isRequireError
=
true
panic
(
fmt
.
Sprintf
(
"stack = %d, req = %d"
,
stack
.
Len
(),
m
))
}
...
...
@@ -105,7 +105,7 @@ func (vm *Vm) RunClosure(closure *Closure, hook DebugHook) (ret []byte, err erro
// TODO Get each instruction cost properly
gas
:=
new
(
big
.
Int
)
useGas
:=
func
(
amount
*
big
.
Int
)
{
gas
.
Add
(
gas
,
amount
)
gas
.
Add
(
gas
,
new
(
big
.
Int
)
.
Mul
(
amount
,
closure
.
Price
)
)
}
switch
op
{
...
...
@@ -142,6 +142,7 @@ func (vm *Vm) RunClosure(closure *Closure, hook DebugHook) (ret []byte, err erro
return
closure
.
Return
(
nil
),
fmt
.
Errorf
(
"insufficient gas %v %v"
,
closure
.
Gas
,
gas
)
}
closure
.
Gas
.
Sub
(
closure
.
Gas
,
gas
)
switch
op
{
case
oLOG
:
...
...
@@ -411,7 +412,7 @@ func (vm *Vm) RunClosure(closure *Closure, hook DebugHook) (ret []byte, err erro
// 0x60 range
case
oCREATE
:
case
oCALL
:
require
(
8
)
require
(
7
)
// Closure addr
addr
:=
stack
.
Pop
()
// Pop gas and value of the stack.
...
...
@@ -425,7 +426,7 @@ func (vm *Vm) RunClosure(closure *Closure, hook DebugHook) (ret []byte, err erro
// Fetch the contract which will serve as the closure body
contract
:=
vm
.
state
.
GetContract
(
addr
.
Bytes
())
// Create a new callable closure
closure
:=
NewClosure
(
closure
,
contract
,
contract
.
script
,
vm
.
state
,
gas
,
value
)
closure
:=
NewClosure
(
closure
,
contract
,
contract
.
script
,
vm
.
state
,
gas
,
closure
.
Price
,
value
)
// Executer the closure and get the return value (if any)
ret
,
err
:=
closure
.
Call
(
vm
,
args
,
hook
)
if
err
!=
nil
{
...
...
ethchain/vm_test.go
View file @
a96c8c8a
...
...
@@ -91,10 +91,10 @@ func TestRun4(t *testing.T) {
exit()
`
),
false
)
script
:=
ethutil
.
Assemble
(
asm
...
)
tx
:=
NewContractCreationTx
(
ethutil
.
Big
(
"0"
),
ethutil
.
Big
(
"1000"
),
script
)
tx
:=
NewContractCreationTx
(
ethutil
.
Big
(
"0"
),
ethutil
.
Big
(
"1000"
),
script
,
nil
)
addr
:=
tx
.
Hash
()[
12
:
]
contract
:=
MakeContract
(
tx
,
state
)
state
.
Update
Contra
ct
(
contract
)
state
.
Update
StateObje
ct
(
contract
)
fmt
.
Printf
(
"%x
\n
"
,
addr
)
asm
,
err
=
mutan
.
Compile
(
strings
.
NewReader
(
`
...
...
@@ -122,12 +122,13 @@ func TestRun4(t *testing.T) {
fmt
.
Println
(
asm
)
callerScript
:=
ethutil
.
Assemble
(
asm
...
)
callerTx
:=
NewContractCreationTx
(
ethutil
.
Big
(
"0"
),
ethutil
.
Big
(
"1000"
),
callerScript
)
callerTx
:=
NewContractCreationTx
(
ethutil
.
Big
(
"0"
),
ethutil
.
Big
(
"1000"
),
callerScript
,
nil
)
// Contract addr as test address
account
:=
NewAccount
(
ContractAddr
,
big
.
NewInt
(
10000000
))
fmt
.
Println
(
account
)
c
:=
MakeContract
(
callerTx
,
state
)
callerClosure
:=
NewClosure
(
account
,
c
,
c
.
script
,
state
,
big
.
NewInt
(
1000000000
),
new
(
big
.
Int
))
callerClosure
:=
NewClosure
(
account
,
c
,
c
.
script
,
state
,
big
.
NewInt
(
1000000000
),
big
.
NewInt
(
10
),
big
.
NewInt
(
0
))
vm
:=
NewVm
(
state
,
RuntimeVars
{
Origin
:
account
.
Address
(),
...
...
@@ -136,10 +137,12 @@ func TestRun4(t *testing.T) {
Coinbase
:
ethutil
.
FromHex
(
"2adc25665018aa1fe0e6bc666dac8fc2697ff9ba"
),
Time
:
1
,
Diff
:
big
.
NewInt
(
256
),
// XXX Tx data? Could be just an argument to the closure instead
TxData
:
nil
,
})
callerClosure
.
Call
(
vm
,
nil
,
nil
)
_
,
e
:=
callerClosure
.
Call
(
vm
,
nil
,
nil
)
if
e
!=
nil
{
fmt
.
Println
(
"error"
,
e
)
}
fmt
.
Println
(
account
)
}
func
TestRun5
(
t
*
testing
.
T
)
{
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment