You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

859 lines
22 KiB

9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
  1. package vm
  2. import (
  3. "bytes"
  4. "errors"
  5. "fmt"
  6. "math/big"
  7. . "github.com/tendermint/tendermint/common"
  8. "github.com/tendermint/tendermint/events"
  9. "github.com/tendermint/tendermint/types"
  10. "github.com/tendermint/tendermint/vm/sha3"
  11. )
  12. var (
  13. ErrUnknownAddress = errors.New("Unknown address")
  14. ErrInsufficientBalance = errors.New("Insufficient balance")
  15. ErrInvalidJumpDest = errors.New("Invalid jump dest")
  16. ErrInsufficientGas = errors.New("Insuffient gas")
  17. ErrMemoryOutOfBounds = errors.New("Memory out of bounds")
  18. ErrCodeOutOfBounds = errors.New("Code out of bounds")
  19. ErrInputOutOfBounds = errors.New("Input out of bounds")
  20. ErrCallStackOverflow = errors.New("Call stack overflow")
  21. ErrCallStackUnderflow = errors.New("Call stack underflow")
  22. ErrDataStackOverflow = errors.New("Data stack overflow")
  23. ErrDataStackUnderflow = errors.New("Data stack underflow")
  24. ErrInvalidContract = errors.New("Invalid contract")
  25. )
  26. type Debug bool
  27. const (
  28. dataStackCapacity = 1024
  29. callStackCapacity = 100 // TODO ensure usage.
  30. memoryCapacity = 1024 * 1024 // 1 MB
  31. dbg Debug = true
  32. )
  33. func (d Debug) Printf(s string, a ...interface{}) {
  34. if d {
  35. fmt.Printf(s, a...)
  36. }
  37. }
  38. type VM struct {
  39. appState AppState
  40. params Params
  41. origin Word256
  42. txid []byte
  43. callDepth int
  44. evc events.Fireable
  45. }
  46. func NewVM(appState AppState, params Params, origin Word256, txid []byte) *VM {
  47. return &VM{
  48. appState: appState,
  49. params: params,
  50. origin: origin,
  51. callDepth: 0,
  52. txid: txid,
  53. }
  54. }
  55. // satisfies events.Eventable
  56. func (vm *VM) SetFireable(evc events.Fireable) {
  57. vm.evc = evc
  58. }
  59. // CONTRACT appState is aware of caller and callee, so we can just mutate them.
  60. // value: To be transferred from caller to callee. Refunded upon error.
  61. // gas: Available gas. No refunds for gas.
  62. // code: May be nil, since the CALL opcode may be used to send value from contracts to accounts
  63. func (vm *VM) Call(caller, callee *Account, code, input []byte, value uint64, gas *uint64) (output []byte, err error) {
  64. exception := new(string)
  65. defer func() {
  66. if vm.evc != nil {
  67. vm.evc.FireEvent(types.EventStringAccReceive(callee.Address.Postfix(20)), types.EventMsgCall{
  68. &types.CallData{caller.Address.Postfix(20), callee.Address.Postfix(20), input, value, *gas},
  69. vm.origin.Postfix(20),
  70. vm.txid,
  71. output,
  72. *exception,
  73. })
  74. }
  75. }()
  76. if err = transfer(caller, callee, value); err != nil {
  77. *exception = err.Error()
  78. return
  79. }
  80. if len(code) > 0 {
  81. vm.callDepth += 1
  82. output, err = vm.call(caller, callee, code, input, value, gas)
  83. vm.callDepth -= 1
  84. if err != nil {
  85. *exception = err.Error()
  86. err := transfer(callee, caller, value)
  87. if err != nil {
  88. panic("Could not return value to caller")
  89. }
  90. }
  91. }
  92. return
  93. }
  94. // Just like Call() but does not transfer 'value' or modify the callDepth.
  95. func (vm *VM) call(caller, callee *Account, code, input []byte, value uint64, gas *uint64) (output []byte, err error) {
  96. dbg.Printf("(%d) (%X) %X (code=%d) gas: %v (d) %X\n", vm.callDepth, caller.Address[:4], callee.Address, len(callee.Code), *gas, input)
  97. var (
  98. pc uint64 = 0
  99. stack = NewStack(dataStackCapacity, gas, &err)
  100. memory = make([]byte, memoryCapacity)
  101. ok = false // convenience
  102. )
  103. for {
  104. // If there is an error, return
  105. if err != nil {
  106. return nil, err
  107. }
  108. var op = codeGetOp(code, pc)
  109. dbg.Printf("(pc) %-3d (op) %-14s (st) %-4d ", pc, op.String(), stack.Len())
  110. switch op {
  111. case STOP: // 0x00
  112. return nil, nil
  113. case ADD: // 0x01
  114. x, y := stack.Pop(), stack.Pop()
  115. xb := new(big.Int).SetBytes(x[:])
  116. yb := new(big.Int).SetBytes(y[:])
  117. sum := new(big.Int).Add(xb, yb)
  118. res := LeftPadWord256(U256(sum).Bytes())
  119. stack.Push(res)
  120. dbg.Printf(" %v + %v = %v (%X)\n", xb, yb, sum, res)
  121. case MUL: // 0x02
  122. x, y := stack.Pop(), stack.Pop()
  123. xb := new(big.Int).SetBytes(x[:])
  124. yb := new(big.Int).SetBytes(y[:])
  125. prod := new(big.Int).Mul(xb, yb)
  126. res := LeftPadWord256(U256(prod).Bytes())
  127. stack.Push(res)
  128. dbg.Printf(" %v * %v = %v (%X)\n", xb, yb, prod, res)
  129. case SUB: // 0x03
  130. x, y := stack.Pop(), stack.Pop()
  131. xb := new(big.Int).SetBytes(x[:])
  132. yb := new(big.Int).SetBytes(y[:])
  133. diff := new(big.Int).Sub(xb, yb)
  134. res := LeftPadWord256(U256(diff).Bytes())
  135. stack.Push(res)
  136. dbg.Printf(" %v - %v = %v (%X)\n", xb, yb, diff, res)
  137. case DIV: // 0x04
  138. x, y := stack.Pop(), stack.Pop()
  139. if y.IsZero() {
  140. stack.Push(Zero256)
  141. dbg.Printf(" %x / %x = %v\n", x, y, 0)
  142. } else {
  143. xb := new(big.Int).SetBytes(x[:])
  144. yb := new(big.Int).SetBytes(y[:])
  145. div := new(big.Int).Div(xb, yb)
  146. res := LeftPadWord256(U256(div).Bytes())
  147. stack.Push(res)
  148. dbg.Printf(" %v / %v = %v (%X)\n", xb, yb, div, res)
  149. }
  150. case SDIV: // 0x05
  151. x, y := stack.Pop(), stack.Pop()
  152. if y.IsZero() {
  153. stack.Push(Zero256)
  154. dbg.Printf(" %x / %x = %v\n", x, y, 0)
  155. } else {
  156. xb := S256(new(big.Int).SetBytes(x[:]))
  157. yb := S256(new(big.Int).SetBytes(y[:]))
  158. div := new(big.Int).Div(xb, yb)
  159. res := LeftPadWord256(U256(div).Bytes())
  160. stack.Push(res)
  161. dbg.Printf(" %v / %v = %v (%X)\n", xb, yb, div, res)
  162. }
  163. case MOD: // 0x06
  164. x, y := stack.Pop(), stack.Pop()
  165. if y.IsZero() {
  166. stack.Push(Zero256)
  167. dbg.Printf(" %v %% %v = %v\n", x, y, 0)
  168. } else {
  169. xb := new(big.Int).SetBytes(x[:])
  170. yb := new(big.Int).SetBytes(y[:])
  171. mod := new(big.Int).Mod(xb, yb)
  172. res := LeftPadWord256(U256(mod).Bytes())
  173. stack.Push(res)
  174. dbg.Printf(" %v %% %v = %v (%X)\n", xb, yb, mod, res)
  175. }
  176. case SMOD: // 0x07
  177. x, y := stack.Pop(), stack.Pop()
  178. if y.IsZero() {
  179. stack.Push(Zero256)
  180. dbg.Printf(" %v %% %v = %v\n", x, y, 0)
  181. } else {
  182. xb := S256(new(big.Int).SetBytes(x[:]))
  183. yb := S256(new(big.Int).SetBytes(y[:]))
  184. mod := new(big.Int).Mod(xb, yb)
  185. res := LeftPadWord256(U256(mod).Bytes())
  186. stack.Push(res)
  187. dbg.Printf(" %v %% %v = %v (%X)\n", xb, yb, mod, res)
  188. }
  189. case ADDMOD: // 0x08
  190. x, y, z := stack.Pop(), stack.Pop(), stack.Pop()
  191. if z.IsZero() {
  192. stack.Push(Zero256)
  193. dbg.Printf(" %v %% %v = %v\n", x, y, 0)
  194. } else {
  195. xb := new(big.Int).SetBytes(x[:])
  196. yb := new(big.Int).SetBytes(y[:])
  197. zb := new(big.Int).SetBytes(z[:])
  198. add := new(big.Int).Add(xb, yb)
  199. mod := new(big.Int).Mod(add, zb)
  200. res := LeftPadWord256(U256(mod).Bytes())
  201. stack.Push(res)
  202. dbg.Printf(" %v + %v %% %v = %v (%X)\n",
  203. xb, yb, zb, mod, res)
  204. }
  205. case MULMOD: // 0x09
  206. x, y, z := stack.Pop(), stack.Pop(), stack.Pop()
  207. if z.IsZero() {
  208. stack.Push(Zero256)
  209. dbg.Printf(" %v %% %v = %v\n", x, y, 0)
  210. } else {
  211. xb := new(big.Int).SetBytes(x[:])
  212. yb := new(big.Int).SetBytes(y[:])
  213. zb := new(big.Int).SetBytes(z[:])
  214. mul := new(big.Int).Mul(xb, yb)
  215. mod := new(big.Int).Mod(mul, zb)
  216. res := LeftPadWord256(U256(mod).Bytes())
  217. stack.Push(res)
  218. dbg.Printf(" %v * %v %% %v = %v (%X)\n",
  219. xb, yb, zb, mod, res)
  220. }
  221. case EXP: // 0x0A
  222. x, y := stack.Pop(), stack.Pop()
  223. xb := new(big.Int).SetBytes(x[:])
  224. yb := new(big.Int).SetBytes(y[:])
  225. pow := new(big.Int).Exp(xb, yb, big.NewInt(0))
  226. res := LeftPadWord256(U256(pow).Bytes())
  227. stack.Push(res)
  228. dbg.Printf(" %v ** %v = %v (%X)\n", xb, yb, pow, res)
  229. case SIGNEXTEND: // 0x0B
  230. back := stack.Pop()
  231. backb := new(big.Int).SetBytes(back[:])
  232. if backb.Cmp(big.NewInt(31)) < 0 {
  233. bit := uint(backb.Uint64()*8 + 7)
  234. num := stack.Pop()
  235. numb := new(big.Int).SetBytes(num[:])
  236. mask := new(big.Int).Lsh(big.NewInt(1), bit)
  237. mask.Sub(mask, big.NewInt(1))
  238. if numb.Bit(int(bit)) == 1 {
  239. numb.Or(numb, mask.Not(mask))
  240. } else {
  241. numb.Add(numb, mask)
  242. }
  243. res := LeftPadWord256(U256(numb).Bytes())
  244. dbg.Printf(" = %v (%X)", numb, res)
  245. stack.Push(res)
  246. }
  247. case LT: // 0x10
  248. x, y := stack.Pop(), stack.Pop()
  249. xb := new(big.Int).SetBytes(x[:])
  250. yb := new(big.Int).SetBytes(y[:])
  251. if xb.Cmp(yb) < 0 {
  252. stack.Push64(1)
  253. dbg.Printf(" %v < %v = %v\n", xb, yb, 1)
  254. } else {
  255. stack.Push(Zero256)
  256. dbg.Printf(" %v < %v = %v\n", xb, yb, 0)
  257. }
  258. case GT: // 0x11
  259. x, y := stack.Pop(), stack.Pop()
  260. xb := new(big.Int).SetBytes(x[:])
  261. yb := new(big.Int).SetBytes(y[:])
  262. if xb.Cmp(yb) > 0 {
  263. stack.Push64(1)
  264. dbg.Printf(" %v > %v = %v\n", xb, yb, 1)
  265. } else {
  266. stack.Push(Zero256)
  267. dbg.Printf(" %v > %v = %v\n", xb, yb, 0)
  268. }
  269. case SLT: // 0x12
  270. x, y := stack.Pop(), stack.Pop()
  271. xb := S256(new(big.Int).SetBytes(x[:]))
  272. yb := S256(new(big.Int).SetBytes(y[:]))
  273. if xb.Cmp(yb) < 0 {
  274. stack.Push64(1)
  275. dbg.Printf(" %v < %v = %v\n", xb, yb, 1)
  276. } else {
  277. stack.Push(Zero256)
  278. dbg.Printf(" %v < %v = %v\n", xb, yb, 0)
  279. }
  280. case SGT: // 0x13
  281. x, y := stack.Pop(), stack.Pop()
  282. xb := S256(new(big.Int).SetBytes(x[:]))
  283. yb := S256(new(big.Int).SetBytes(y[:]))
  284. if xb.Cmp(yb) > 0 {
  285. stack.Push64(1)
  286. dbg.Printf(" %v > %v = %v\n", xb, yb, 1)
  287. } else {
  288. stack.Push(Zero256)
  289. dbg.Printf(" %v > %v = %v\n", xb, yb, 0)
  290. }
  291. case EQ: // 0x14
  292. x, y := stack.Pop(), stack.Pop()
  293. if bytes.Equal(x[:], y[:]) {
  294. stack.Push64(1)
  295. dbg.Printf(" %X == %X = %v\n", x, y, 1)
  296. } else {
  297. stack.Push(Zero256)
  298. dbg.Printf(" %X == %X = %v\n", x, y, 0)
  299. }
  300. case ISZERO: // 0x15
  301. x := stack.Pop()
  302. if x.IsZero() {
  303. stack.Push64(1)
  304. dbg.Printf(" %v == 0 = %v\n", x, 1)
  305. } else {
  306. stack.Push(Zero256)
  307. dbg.Printf(" %v == 0 = %v\n", x, 0)
  308. }
  309. case AND: // 0x16
  310. x, y := stack.Pop(), stack.Pop()
  311. z := [32]byte{}
  312. for i := 0; i < 32; i++ {
  313. z[i] = x[i] & y[i]
  314. }
  315. stack.Push(z)
  316. dbg.Printf(" %X & %X = %X\n", x, y, z)
  317. case OR: // 0x17
  318. x, y := stack.Pop(), stack.Pop()
  319. z := [32]byte{}
  320. for i := 0; i < 32; i++ {
  321. z[i] = x[i] | y[i]
  322. }
  323. stack.Push(z)
  324. dbg.Printf(" %X | %X = %X\n", x, y, z)
  325. case XOR: // 0x18
  326. x, y := stack.Pop(), stack.Pop()
  327. z := [32]byte{}
  328. for i := 0; i < 32; i++ {
  329. z[i] = x[i] ^ y[i]
  330. }
  331. stack.Push(z)
  332. dbg.Printf(" %X ^ %X = %X\n", x, y, z)
  333. case NOT: // 0x19
  334. x := stack.Pop()
  335. z := [32]byte{}
  336. for i := 0; i < 32; i++ {
  337. z[i] = ^x[i]
  338. }
  339. stack.Push(z)
  340. dbg.Printf(" !%X = %X\n", x, z)
  341. case BYTE: // 0x1A
  342. idx, val := stack.Pop64(), stack.Pop()
  343. res := byte(0)
  344. if idx < 32 {
  345. res = val[idx]
  346. }
  347. stack.Push64(uint64(res))
  348. dbg.Printf(" => 0x%X\n", res)
  349. case SHA3: // 0x20
  350. if ok = useGas(gas, GasSha3); !ok {
  351. return nil, firstErr(err, ErrInsufficientGas)
  352. }
  353. offset, size := stack.Pop64(), stack.Pop64()
  354. data, ok := subslice(memory, offset, size)
  355. if !ok {
  356. return nil, firstErr(err, ErrMemoryOutOfBounds)
  357. }
  358. data = sha3.Sha3(data)
  359. stack.PushBytes(data)
  360. dbg.Printf(" => (%v) %X\n", size, data)
  361. case ADDRESS: // 0x30
  362. stack.Push(callee.Address)
  363. dbg.Printf(" => %X\n", callee.Address)
  364. case BALANCE: // 0x31
  365. addr := stack.Pop()
  366. if ok = useGas(gas, GasGetAccount); !ok {
  367. return nil, firstErr(err, ErrInsufficientGas)
  368. }
  369. acc := vm.appState.GetAccount(addr)
  370. if acc == nil {
  371. return nil, firstErr(err, ErrUnknownAddress)
  372. }
  373. balance := acc.Balance
  374. stack.Push64(balance)
  375. dbg.Printf(" => %v (%X)\n", balance, addr)
  376. case ORIGIN: // 0x32
  377. stack.Push(vm.origin)
  378. dbg.Printf(" => %X\n", vm.origin)
  379. case CALLER: // 0x33
  380. stack.Push(caller.Address)
  381. dbg.Printf(" => %X\n", caller.Address)
  382. case CALLVALUE: // 0x34
  383. stack.Push64(value)
  384. dbg.Printf(" => %v\n", value)
  385. case CALLDATALOAD: // 0x35
  386. offset := stack.Pop64()
  387. data, ok := subslice(input, offset, 32)
  388. if !ok {
  389. return nil, firstErr(err, ErrInputOutOfBounds)
  390. }
  391. res := LeftPadWord256(data)
  392. stack.Push(res)
  393. dbg.Printf(" => 0x%X\n", res)
  394. case CALLDATASIZE: // 0x36
  395. stack.Push64(uint64(len(input)))
  396. dbg.Printf(" => %d\n", len(input))
  397. case CALLDATACOPY: // 0x37
  398. memOff := stack.Pop64()
  399. inputOff := stack.Pop64()
  400. length := stack.Pop64()
  401. data, ok := subslice(input, inputOff, length)
  402. if !ok {
  403. return nil, firstErr(err, ErrInputOutOfBounds)
  404. }
  405. dest, ok := subslice(memory, memOff, length)
  406. if !ok {
  407. return nil, firstErr(err, ErrMemoryOutOfBounds)
  408. }
  409. copy(dest, data)
  410. dbg.Printf(" => [%v, %v, %v] %X\n", memOff, inputOff, length, data)
  411. case CODESIZE: // 0x38
  412. l := uint64(len(code))
  413. stack.Push64(l)
  414. dbg.Printf(" => %d\n", l)
  415. case CODECOPY: // 0x39
  416. memOff := stack.Pop64()
  417. codeOff := stack.Pop64()
  418. length := stack.Pop64()
  419. data, ok := subslice(code, codeOff, length)
  420. if !ok {
  421. return nil, firstErr(err, ErrCodeOutOfBounds)
  422. }
  423. dest, ok := subslice(memory, memOff, length)
  424. if !ok {
  425. return nil, firstErr(err, ErrMemoryOutOfBounds)
  426. }
  427. copy(dest, data)
  428. dbg.Printf(" => [%v, %v, %v] %X\n", memOff, codeOff, length, data)
  429. case GASPRICE_DEPRECATED: // 0x3A
  430. stack.Push(Zero256)
  431. dbg.Printf(" => %X (GASPRICE IS DEPRECATED)\n")
  432. case EXTCODESIZE: // 0x3B
  433. addr := stack.Pop()
  434. if ok = useGas(gas, GasGetAccount); !ok {
  435. return nil, firstErr(err, ErrInsufficientGas)
  436. }
  437. acc := vm.appState.GetAccount(addr)
  438. if acc == nil {
  439. return nil, firstErr(err, ErrUnknownAddress)
  440. }
  441. code := acc.Code
  442. l := uint64(len(code))
  443. stack.Push64(l)
  444. dbg.Printf(" => %d\n", l)
  445. case EXTCODECOPY: // 0x3C
  446. addr := stack.Pop()
  447. if ok = useGas(gas, GasGetAccount); !ok {
  448. return nil, firstErr(err, ErrInsufficientGas)
  449. }
  450. acc := vm.appState.GetAccount(addr)
  451. if acc == nil {
  452. return nil, firstErr(err, ErrUnknownAddress)
  453. }
  454. code := acc.Code
  455. memOff := stack.Pop64()
  456. codeOff := stack.Pop64()
  457. length := stack.Pop64()
  458. data, ok := subslice(code, codeOff, length)
  459. if !ok {
  460. return nil, firstErr(err, ErrCodeOutOfBounds)
  461. }
  462. dest, ok := subslice(memory, memOff, length)
  463. if !ok {
  464. return nil, firstErr(err, ErrMemoryOutOfBounds)
  465. }
  466. copy(dest, data)
  467. dbg.Printf(" => [%v, %v, %v] %X\n", memOff, codeOff, length, data)
  468. case BLOCKHASH: // 0x40
  469. stack.Push(Zero256)
  470. dbg.Printf(" => 0x%X (NOT SUPPORTED)\n", stack.Peek().Bytes())
  471. case COINBASE: // 0x41
  472. stack.Push(Zero256)
  473. dbg.Printf(" => 0x%X (NOT SUPPORTED)\n", stack.Peek().Bytes())
  474. case TIMESTAMP: // 0x42
  475. time := vm.params.BlockTime
  476. stack.Push64(uint64(time))
  477. dbg.Printf(" => 0x%X\n", time)
  478. case BLOCKHEIGHT: // 0x43
  479. number := uint64(vm.params.BlockHeight)
  480. stack.Push64(number)
  481. dbg.Printf(" => 0x%X\n", number)
  482. case GASLIMIT: // 0x45
  483. stack.Push64(vm.params.GasLimit)
  484. dbg.Printf(" => %v\n", vm.params.GasLimit)
  485. case POP: // 0x50
  486. stack.Pop()
  487. dbg.Printf(" => %v\n", vm.params.GasLimit)
  488. case MLOAD: // 0x51
  489. offset := stack.Pop64()
  490. data, ok := subslice(memory, offset, 32)
  491. if !ok {
  492. return nil, firstErr(err, ErrMemoryOutOfBounds)
  493. }
  494. stack.Push(LeftPadWord256(data))
  495. dbg.Printf(" => 0x%X\n", data)
  496. case MSTORE: // 0x52
  497. offset, data := stack.Pop64(), stack.Pop()
  498. dest, ok := subslice(memory, offset, 32)
  499. if !ok {
  500. return nil, firstErr(err, ErrMemoryOutOfBounds)
  501. }
  502. copy(dest, data[:])
  503. dbg.Printf(" => 0x%X\n", data)
  504. case MSTORE8: // 0x53
  505. offset, val := stack.Pop64(), byte(stack.Pop64()&0xFF)
  506. if len(memory) <= int(offset) {
  507. return nil, firstErr(err, ErrMemoryOutOfBounds)
  508. }
  509. memory[offset] = val
  510. dbg.Printf(" => [%v] 0x%X\n", offset, val)
  511. case SLOAD: // 0x54
  512. loc := stack.Pop()
  513. data := vm.appState.GetStorage(callee.Address, loc)
  514. stack.Push(data)
  515. dbg.Printf(" {0x%X : 0x%X}\n", loc, data)
  516. case SSTORE: // 0x55
  517. loc, data := stack.Pop(), stack.Pop()
  518. vm.appState.SetStorage(callee.Address, loc, data)
  519. useGas(gas, GasStorageUpdate)
  520. dbg.Printf(" {0x%X : 0x%X}\n", loc, data)
  521. case JUMP: // 0x56
  522. err = jump(code, stack.Pop64(), &pc)
  523. continue
  524. case JUMPI: // 0x57
  525. pos, cond := stack.Pop64(), stack.Pop()
  526. if !cond.IsZero() {
  527. err = jump(code, pos, &pc)
  528. continue
  529. }
  530. dbg.Printf(" ~> false\n")
  531. case PC: // 0x58
  532. stack.Push64(pc)
  533. case MSIZE: // 0x59
  534. stack.Push64(uint64(len(memory)))
  535. case GAS: // 0x5A
  536. stack.Push64(*gas)
  537. dbg.Printf(" => %X\n", *gas)
  538. case JUMPDEST: // 0x5B
  539. dbg.Printf("\n")
  540. // Do nothing
  541. case PUSH1, PUSH2, PUSH3, PUSH4, PUSH5, PUSH6, PUSH7, PUSH8, PUSH9, PUSH10, PUSH11, PUSH12, PUSH13, PUSH14, PUSH15, PUSH16, PUSH17, PUSH18, PUSH19, PUSH20, PUSH21, PUSH22, PUSH23, PUSH24, PUSH25, PUSH26, PUSH27, PUSH28, PUSH29, PUSH30, PUSH31, PUSH32:
  542. a := uint64(op - PUSH1 + 1)
  543. codeSegment, ok := subslice(code, pc+1, a)
  544. if !ok {
  545. return nil, firstErr(err, ErrCodeOutOfBounds)
  546. }
  547. res := LeftPadWord256(codeSegment)
  548. stack.Push(res)
  549. pc += a
  550. dbg.Printf(" => 0x%X\n", res)
  551. //stack.Print(10)
  552. case DUP1, DUP2, DUP3, DUP4, DUP5, DUP6, DUP7, DUP8, DUP9, DUP10, DUP11, DUP12, DUP13, DUP14, DUP15, DUP16:
  553. n := int(op - DUP1 + 1)
  554. stack.Dup(n)
  555. dbg.Printf(" => [%d] 0x%X\n", n, stack.Peek().Bytes())
  556. case SWAP1, SWAP2, SWAP3, SWAP4, SWAP5, SWAP6, SWAP7, SWAP8, SWAP9, SWAP10, SWAP11, SWAP12, SWAP13, SWAP14, SWAP15, SWAP16:
  557. n := int(op - SWAP1 + 2)
  558. stack.Swap(n)
  559. dbg.Printf(" => [%d] %X\n", n, stack.Peek())
  560. //stack.Print(10)
  561. case LOG0, LOG1, LOG2, LOG3, LOG4:
  562. n := int(op - LOG0)
  563. topics := make([]Word256, n)
  564. offset, size := stack.Pop64(), stack.Pop64()
  565. for i := 0; i < n; i++ {
  566. topics[i] = stack.Pop()
  567. }
  568. data, ok := subslice(memory, offset, size)
  569. if !ok {
  570. return nil, firstErr(err, ErrMemoryOutOfBounds)
  571. }
  572. log := &Log{
  573. callee.Address,
  574. topics,
  575. data,
  576. vm.params.BlockHeight,
  577. }
  578. vm.appState.AddLog(log)
  579. dbg.Printf(" => %v\n", log)
  580. case CREATE: // 0xF0
  581. contractValue := stack.Pop64()
  582. offset, size := stack.Pop64(), stack.Pop64()
  583. input, ok := subslice(memory, offset, size)
  584. if !ok {
  585. return nil, firstErr(err, ErrMemoryOutOfBounds)
  586. }
  587. // Check balance
  588. if callee.Balance < contractValue {
  589. return nil, firstErr(err, ErrInsufficientBalance)
  590. }
  591. // TODO charge for gas to create account _ the code length * GasCreateByte
  592. newAccount := vm.appState.CreateAccount(callee)
  593. // Run the input to get the contract code.
  594. ret, err_ := vm.Call(callee, newAccount, input, input, contractValue, gas)
  595. if err_ != nil {
  596. stack.Push(Zero256)
  597. } else {
  598. newAccount.Code = ret // Set the code
  599. stack.Push(newAccount.Address)
  600. }
  601. case CALL, CALLCODE: // 0xF1, 0xF2
  602. gasLimit := stack.Pop64()
  603. addr, value := stack.Pop(), stack.Pop64()
  604. inOffset, inSize := stack.Pop64(), stack.Pop64() // inputs
  605. retOffset, retSize := stack.Pop64(), stack.Pop64() // outputs
  606. dbg.Printf(" => %X\n", addr)
  607. // Get the arguments from the memory
  608. args, ok := subslice(memory, inOffset, inSize)
  609. if !ok {
  610. return nil, firstErr(err, ErrMemoryOutOfBounds)
  611. }
  612. // Ensure that gasLimit is reasonable
  613. if *gas < gasLimit {
  614. return nil, firstErr(err, ErrInsufficientGas)
  615. } else {
  616. *gas -= gasLimit
  617. // NOTE: we will return any used gas later.
  618. }
  619. // Begin execution
  620. var ret []byte
  621. var err error
  622. if nativeContract := nativeContracts[addr]; nativeContract != nil {
  623. // Native contract
  624. ret, err = nativeContract(args, &gasLimit)
  625. } else {
  626. // EVM contract
  627. if ok = useGas(gas, GasGetAccount); !ok {
  628. return nil, firstErr(err, ErrInsufficientGas)
  629. }
  630. acc := vm.appState.GetAccount(addr)
  631. // since CALL is used also for sending funds,
  632. // acc may not exist yet. This is an error for
  633. // CALLCODE, but not for CALL, though I don't think
  634. // ethereum actually cares
  635. if op == CALLCODE {
  636. if acc == nil {
  637. return nil, firstErr(err, ErrUnknownAddress)
  638. }
  639. ret, err = vm.Call(callee, callee, acc.Code, args, value, gas)
  640. } else {
  641. if acc == nil {
  642. // if we have not seen the account before, create it
  643. // so we can send funds
  644. acc = &Account{
  645. Address: addr,
  646. }
  647. vm.appState.UpdateAccount(acc)
  648. }
  649. ret, err = vm.Call(callee, acc, acc.Code, args, value, gas)
  650. }
  651. }
  652. // Push result
  653. if err != nil {
  654. dbg.Printf("error on call: %s", err.Error())
  655. // TODO: fire event
  656. stack.Push(Zero256)
  657. } else {
  658. stack.Push(One256)
  659. dest, ok := subslice(memory, retOffset, retSize)
  660. if !ok {
  661. return nil, firstErr(err, ErrMemoryOutOfBounds)
  662. }
  663. copy(dest, ret)
  664. }
  665. // Handle remaining gas.
  666. *gas += gasLimit
  667. dbg.Printf("resume %X (%v)\n", callee.Address, gas)
  668. case RETURN: // 0xF3
  669. offset, size := stack.Pop64(), stack.Pop64()
  670. ret, ok := subslice(memory, offset, size)
  671. if !ok {
  672. return nil, firstErr(err, ErrMemoryOutOfBounds)
  673. }
  674. dbg.Printf(" => [%v, %v] (%d) 0x%X\n", offset, size, len(ret), ret)
  675. return ret, nil
  676. case SUICIDE: // 0xFF
  677. addr := stack.Pop()
  678. if ok = useGas(gas, GasGetAccount); !ok {
  679. return nil, firstErr(err, ErrInsufficientGas)
  680. }
  681. // TODO if the receiver is , then make it the fee.
  682. receiver := vm.appState.GetAccount(addr)
  683. if receiver == nil {
  684. return nil, firstErr(err, ErrUnknownAddress)
  685. }
  686. balance := callee.Balance
  687. receiver.Balance += balance
  688. vm.appState.UpdateAccount(receiver)
  689. vm.appState.RemoveAccount(callee)
  690. dbg.Printf(" => (%X) %v\n", addr[:4], balance)
  691. fallthrough
  692. default:
  693. dbg.Printf("(pc) %-3v Invalid opcode %X\n", pc, op)
  694. panic(fmt.Errorf("Invalid opcode %X", op))
  695. }
  696. pc++
  697. }
  698. }
  699. func subslice(data []byte, offset, length uint64) (ret []byte, ok bool) {
  700. size := uint64(len(data))
  701. if size < offset {
  702. return nil, false
  703. } else if size < offset+length {
  704. ret, ok = data[offset:], true
  705. ret = RightPadBytes(ret, 32)
  706. } else {
  707. ret, ok = data[offset:offset+length], true
  708. }
  709. return
  710. }
  711. func rightMostBytes(data []byte, n int) []byte {
  712. size := MinInt(len(data), n)
  713. offset := len(data) - size
  714. return data[offset:]
  715. }
  716. func codeGetOp(code []byte, n uint64) OpCode {
  717. if uint64(len(code)) <= n {
  718. return OpCode(0) // stop
  719. } else {
  720. return OpCode(code[n])
  721. }
  722. }
  723. func jump(code []byte, to uint64, pc *uint64) (err error) {
  724. dest := codeGetOp(code, to)
  725. if dest != JUMPDEST {
  726. dbg.Printf(" ~> %v invalid jump dest %v\n", to, dest)
  727. return ErrInvalidJumpDest
  728. }
  729. dbg.Printf(" ~> %v\n", to)
  730. *pc = to
  731. return nil
  732. }
  733. func firstErr(errA, errB error) error {
  734. if errA != nil {
  735. return errA
  736. } else {
  737. return errB
  738. }
  739. }
  740. func useGas(gas *uint64, gasToUse uint64) bool {
  741. if *gas > gasToUse {
  742. *gas -= gasToUse
  743. return true
  744. } else {
  745. return false
  746. }
  747. }
  748. func transfer(from, to *Account, amount uint64) error {
  749. if from.Balance < amount {
  750. return ErrInsufficientBalance
  751. } else {
  752. from.Balance -= amount
  753. to.Balance += amount
  754. return nil
  755. }
  756. }