neo-go/pkg/compiler/panic_test.go
Evgenii Stratonikov 51ae12e4fd *: move syscall handling out of VM
Remove interop-related structures from the `vm` package.

Signed-off-by: Evgenii Stratonikov <evgeniy@nspcc.ru>
2020-07-29 13:41:08 +03:00

69 lines
1.5 KiB
Go

package compiler_test
import (
"errors"
"fmt"
"math/big"
"testing"
"github.com/nspcc-dev/neo-go/pkg/vm"
"github.com/nspcc-dev/neo-go/pkg/vm/emit"
"github.com/stretchr/testify/require"
)
func TestPanic(t *testing.T) {
t.Run("no panic", func(t *testing.T) {
src := getPanicSource(false, `"execution fault"`)
eval(t, src, big.NewInt(7))
})
t.Run("panic with message", func(t *testing.T) {
var logs []string
src := getPanicSource(true, `"execution fault"`)
v := vmAndCompile(t, src)
v.SyscallHandler = getLogHandler(&logs)
require.Error(t, v.Run())
require.True(t, v.HasFailed())
require.Equal(t, 1, len(logs))
require.Equal(t, "execution fault", logs[0])
})
t.Run("panic with nil", func(t *testing.T) {
var logs []string
src := getPanicSource(true, `nil`)
v := vmAndCompile(t, src)
v.SyscallHandler = getLogHandler(&logs)
require.Error(t, v.Run())
require.True(t, v.HasFailed())
require.Equal(t, 0, len(logs))
})
}
func getPanicSource(need bool, message string) string {
return fmt.Sprintf(`
package main
func Main() int {
needPanic := %#v
if needPanic {
panic(%s)
return 5
}
return 7
}
`, need, message)
}
func getLogHandler(logs *[]string) vm.SyscallHandler {
logID := emit.InteropNameToID([]byte("System.Runtime.Log"))
return func(v *vm.VM, id uint32) error {
if id != logID {
return errors.New("syscall not found")
}
msg := string(v.Estack().Pop().Bytes())
*logs = append(*logs, msg)
return nil
}
}