fixed missing syscall transaction.GetHash() (CityOfZion/neo-storm#43)

Several bug fixes and improvements

Imported from CityOfZion/neo-storm (8e8fe5c215bfaed51452482f4f28cc9956a1f69b).
This commit is contained in:
Anthony De Meulemeester 2018-10-23 10:23:03 +02:00 committed by Roman Khimov
parent 69511e053f
commit 459d3654a2
5 changed files with 56 additions and 32 deletions

View file

@ -71,17 +71,6 @@ func NewCommand() cli.Command {
},
},
},
{
Name: "opdump",
Usage: "dump the opcode of a .go file",
Action: contractDumpOpcode,
Flags: []cli.Flag{
cli.StringFlag{
Name: "in, i",
Usage: "Input file for the smart contract",
},
},
},
{
Name: "init",
Usage: "initialize a new smart-contract in a directory with boiler plate code",
@ -97,6 +86,17 @@ func NewCommand() cli.Command {
},
},
},
{
Name: "inspect",
Usage: "creates a user readable dump of the program instructions",
Action: inspect,
Flags: []cli.Flag{
cli.StringFlag{
Name: "in, i",
Usage: "input file of the program",
},
},
},
},
}
}
@ -172,7 +172,7 @@ func testInvoke(ctx *cli.Context) error {
// For now we will hardcode the endpoint.
// On the long term the internal VM will run the script.
// TODO: remove RPC dependency, hardcoded node.
endpoint := "http://seed5.bridgeprotocol.io:10332"
endpoint := "http://node1.ams2.bridgeprotocol.io:10332"
client, err := rpc.NewClient(context.TODO(), endpoint, rpc.ClientOptions{})
if err != nil {
return cli.NewExitError(err, 1)
@ -194,17 +194,6 @@ func testInvoke(ctx *cli.Context) error {
return nil
}
func contractDumpOpcode(ctx *cli.Context) error {
src := ctx.String("in")
if len(src) == 0 {
return cli.NewExitError(errNoInput, 1)
}
if err := compiler.DumpOpcode(src); err != nil {
return cli.NewExitError(err, 1)
}
return nil
}
type ContractDetails struct {
Author string
Email string
@ -259,3 +248,12 @@ func parseContractDetails() ContractDetails {
return details
}
func inspect(ctx *cli.Context) error {
src := ctx.String("in")
if len(src) == 0 {
return cli.NewExitError(errNoInput, 1)
}
compiler.CompileAndInspect(src)
return nil
}

View file

@ -29,8 +29,8 @@ func GetAttributes(t Transaction) []attribute.Attribute {
// FIXME: What is the correct return type for this?
// GetReferences returns a slice of references for the given transaction.
func GetReferences(t Transaction) interface{} {
return 0
func GetReferences(t Transaction) []interface{} {
return []interface{}{}
}
// FIXME: What is the correct return type for this?

View file

@ -8,6 +8,7 @@ import (
"go/token"
"go/types"
"log"
"strconv"
"strings"
"github.com/CityOfZion/neo-go/pkg/crypto"
@ -248,6 +249,21 @@ func (c *codegen) Visit(node ast.Node) ast.Visitor {
default:
log.Fatal("nested selector assigns not supported yet")
}
// Assignments to index expressions.
// slice[0] = 10
case *ast.IndexExpr:
ast.Walk(c, n.Rhs[i])
name := t.X.(*ast.Ident).Name
c.emitLoadLocal(name)
// For now storm only supports basic index operations. Hence we
// cast this to an *ast.BasicLit (1, 2 , 3)
indexStr := t.Index.(*ast.BasicLit).Value
index, err := strconv.Atoi(indexStr)
if err != nil {
log.Fatal("failed to convert slice index to integer")
}
c.emitStoreStructField(index)
}
}
return nil

View file

@ -90,16 +90,15 @@ func CompileAndSave(src string, o *Options) error {
if err != nil {
return fmt.Errorf("Error while trying to compile smart contract file: %v", err)
}
if o.Debug {
log.Println(hex.EncodeToString(b))
}
log.Println(hex.EncodeToString(b))
out := fmt.Sprintf("%s.%s", o.Outfile, o.Ext)
return ioutil.WriteFile(out, b, os.ModePerm)
}
// DumpOpcode compiles the program and dumps the opcode in a user friendly format.
func DumpOpcode(src string) error {
// CompileAndInspect compiles the program and dumps the opcode in a user friendly format.
func CompileAndInspect(src string) error {
b, err := ioutil.ReadFile(src)
if err != nil {
return err
@ -111,8 +110,18 @@ func DumpOpcode(src string) error {
w := tabwriter.NewWriter(os.Stdout, 0, 0, 4, ' ', 0)
fmt.Fprintln(w, "INDEX\tOPCODE\tDESC\t")
for i := 0; i < len(b); i++ {
fmt.Fprintf(w, "%d\t0x%2x\t%s\t\n", i, b[i], vm.Instruction(b[i]))
for i := 0; i <= len(b)-1; {
instr := vm.Instruction(b[i])
if instr >= vm.PUSHBYTES1 && instr <= vm.PUSHBYTES75 {
fmt.Fprintf(w, "%d\t0x%x\t%s\t\n", i, b[i], fmt.Sprintf("PUSHBYTES%d", int(instr)))
for x := 0; x < int(instr); x++ {
fmt.Fprintf(w, "%d\t0x%x\t%s\t\n", i, b[i+1+x], string(b[i+1+x]))
}
i += int(instr) + 1
continue
}
fmt.Fprintf(w, "%d\t0x%x\t%s\t\n", i, b[i], instr)
i++
}
w.Flush()
return nil

View file

@ -43,6 +43,7 @@ var syscalls = map[string]map[string]string{
"GetTransaction": "Neo.Block.GetTransaction",
},
"transaction": {
"GetHash": "Neo.Transaction.GetHash",
"GetType": "Neo.Transaction.GetType",
"GetAttributes": "Neo.Transaction.GetAttributes",
"GetInputs": "Neo.Transaction.GetInputs",