From ee83eaf0740a8ba506aed412f9ac8b7030648a95 Mon Sep 17 00:00:00 2001 From: 6h057 <15034695+omarsy@users.noreply.github.com> Date: Tue, 30 Jul 2024 19:12:47 +0200 Subject: [PATCH 1/7] fix(gnovm): add missing length check in DeclStmt and AssignStmt (#2206) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Closes #2137
Contributors' checklist... - [ ] Added new tests, or not needed, or not feasible - [ ] Provided an example (e.g. screenshot) to aid review or the PR is self-explanatory - [ ] Updated the official documentation or not needed - [ ] No breaking changes were made, or a `BREAKING CHANGE: xxx` message was included in the description - [ ] Added references to related issues and PRs - [ ] Provided any useful hints for running manual tests - [ ] Added new benchmarks to [generated graphs](https://gnoland.github.io/benchmarks), if any. More info [here](https://github.com/gnolang/gno/blob/master/.benchmarks/README.md).
--------- Co-authored-by: Miloš Živković --- gnovm/pkg/gnolang/preprocess.go | 23 +++++++++--- gnovm/pkg/gnolang/type_check.go | 64 +++++++++++++++++++++++++++++++++ gnovm/tests/files/assign24.gno | 8 +++++ gnovm/tests/files/assign25.gno | 14 ++++++++ gnovm/tests/files/assign25b.gno | 14 ++++++++ gnovm/tests/files/assign26.gno | 9 +++++ gnovm/tests/files/assign27.gno | 9 +++++ gnovm/tests/files/assign28.gno | 11 ++++++ gnovm/tests/files/var18.gno | 4 +-- gnovm/tests/files/var19.gno | 11 ++++++ gnovm/tests/files/var20.gno | 12 +++++++ gnovm/tests/files/var21.gno | 14 ++++++++ gnovm/tests/files/var22.gno | 14 ++++++++ gnovm/tests/files/var22b.gno | 14 ++++++++ gnovm/tests/files/var23.gno | 9 +++++ gnovm/tests/files/var24.gno | 9 +++++ gnovm/tests/files/var25.gno | 9 +++++ gnovm/tests/files/var26.gno | 11 ++++++ 18 files changed, 252 insertions(+), 7 deletions(-) create mode 100644 gnovm/tests/files/assign24.gno create mode 100644 gnovm/tests/files/assign25.gno create mode 100644 gnovm/tests/files/assign25b.gno create mode 100644 gnovm/tests/files/assign26.gno create mode 100644 gnovm/tests/files/assign27.gno create mode 100644 gnovm/tests/files/assign28.gno create mode 100644 gnovm/tests/files/var19.gno create mode 100644 gnovm/tests/files/var20.gno create mode 100644 gnovm/tests/files/var21.gno create mode 100644 gnovm/tests/files/var22.gno create mode 100644 gnovm/tests/files/var22b.gno create mode 100644 gnovm/tests/files/var23.gno create mode 100644 gnovm/tests/files/var24.gno create mode 100644 gnovm/tests/files/var25.gno create mode 100644 gnovm/tests/files/var26.gno diff --git a/gnovm/pkg/gnolang/preprocess.go b/gnovm/pkg/gnolang/preprocess.go index d21e9bf0efd..5a710723b86 100644 --- a/gnovm/pkg/gnolang/preprocess.go +++ b/gnovm/pkg/gnolang/preprocess.go @@ -427,6 +427,8 @@ func Preprocess(store Store, ctx BlockNode, n Node) Node { switch n := n.(type) { // TRANS_ENTER ----------------------- case *AssignStmt: + checkValDefineMismatch(n) + if n.Op == DEFINE { for _, lx := range n.Lhs { ln := lx.(*NameExpr).Name @@ -445,7 +447,6 @@ func Preprocess(store Store, ctx BlockNode, n Node) Node { } else { // nothing defined. } - // TRANS_ENTER ----------------------- case *ImportDecl, *ValueDecl, *TypeDecl, *FuncDecl: // NOTE func decl usually must happen with a @@ -457,8 +458,12 @@ func Preprocess(store Store, ctx BlockNode, n Node) Node { // skip declarations already predefined // (e.g. through recursion for a dependent) } else { + d := n.(Decl) + if cd, ok := d.(*ValueDecl); ok { + checkValDefineMismatch(cd) + } // recursively predefine dependencies. - d2, ppd := predefineNow(store, last, n.(Decl)) + d2, ppd := predefineNow(store, last, d) if ppd { return d2, TRANS_SKIP } else { @@ -2162,8 +2167,8 @@ func Preprocess(store Store, ctx BlockNode, n Node) Node { // special case if `var a, b, c T? = f()` form. cx := n.Values[0].(*CallExpr) tt := evalStaticTypeOfRaw(store, last, cx).(*tupleType) - if len(tt.Elts) != numNames { - panic("should not happen") + if rLen := len(tt.Elts); rLen != numNames { + panic(fmt.Sprintf("assignment mismatch: %d variable(s) but %s returns %d value(s)", numNames, cx.Func.String(), rLen)) } if n.Type != nil { // only a single type can be specified. @@ -2182,8 +2187,16 @@ func Preprocess(store Store, ctx BlockNode, n Node) Node { } } } else if len(n.Values) != 0 && numNames != len(n.Values) { - panic("should not happen") + panic(fmt.Sprintf("assignment mismatch: %d variable(s) but %d value(s)", numNames, len(n.Values))) } else { // general case + for _, v := range n.Values { + if cx, ok := v.(*CallExpr); ok { + tt, ok := evalStaticTypeOfRaw(store, last, cx).(*tupleType) + if ok && len(tt.Elts) != 1 { + panic(fmt.Sprintf("multiple-value %s (value of type %s) in single-value context", cx.Func.String(), tt.Elts)) + } + } + } // evaluate types and convert consts. if n.Type != nil { // only a single type can be specified. diff --git a/gnovm/pkg/gnolang/type_check.go b/gnovm/pkg/gnolang/type_check.go index 3f25667f353..31025fef152 100644 --- a/gnovm/pkg/gnolang/type_check.go +++ b/gnovm/pkg/gnolang/type_check.go @@ -215,6 +215,70 @@ func assertAssignableTo(xt, dt Type, autoNative bool) { } } +// checkValDefineMismatch checks for mismatch between the number of variables and values in a ValueDecl or AssignStmt. +func checkValDefineMismatch(n Node) { + var ( + valueDecl *ValueDecl + assign *AssignStmt + values []Expr + numNames int + numValues int + ) + + switch x := n.(type) { + case *ValueDecl: + valueDecl = x + numNames = len(valueDecl.NameExprs) + numValues = len(valueDecl.Values) + values = valueDecl.Values + case *AssignStmt: + if x.Op != DEFINE { + return + } + + assign = x + numNames = len(assign.Lhs) + numValues = len(assign.Rhs) + values = assign.Rhs + default: + panic(fmt.Sprintf("unexpected node type %T", n)) + } + + if numValues == 0 || numValues == numNames { + return + } + + // Special case for single value. + // If the value is a call expression, type assertion, or index expression, + // it can be assigned to multiple variables. + if numValues == 1 { + switch values[0].(type) { + case *CallExpr: + return + case *TypeAssertExpr: + if numNames != 2 { + panic(fmt.Sprintf("assignment mismatch: %d variable(s) but %d value(s)", numNames, numValues)) + } + return + case *IndexExpr: + if numNames != 2 { + panic(fmt.Sprintf("assignment mismatch: %d variable(s) but %d value(s)", numNames, numValues)) + } + return + } + } + + if valueDecl != nil { + if numNames > numValues { + panic(fmt.Sprintf("missing init expr for %s", valueDecl.NameExprs[numValues].String())) + } + + panic(fmt.Sprintf("extra init expr %s", values[numNames].String())) + } + + panic(fmt.Sprintf("assignment mismatch: %d variable(s) but %d value(s)", numNames, numValues)) +} + // Assert that xt can be assigned as dt (dest type). // If autoNative is true, a broad range of xt can match against // a target native dt type, if and only if dt is a native type. diff --git a/gnovm/tests/files/assign24.gno b/gnovm/tests/files/assign24.gno new file mode 100644 index 00000000000..408258def92 --- /dev/null +++ b/gnovm/tests/files/assign24.gno @@ -0,0 +1,8 @@ +package main + +func main() { + a, b := 1 +} + +// Error: +// main/files/assign24.gno:4:2: assignment mismatch: 2 variable(s) but 1 value(s) diff --git a/gnovm/tests/files/assign25.gno b/gnovm/tests/files/assign25.gno new file mode 100644 index 00000000000..b945afc3b1f --- /dev/null +++ b/gnovm/tests/files/assign25.gno @@ -0,0 +1,14 @@ +package main + +func foo() (int, bool) { + return 1, true +} + +func main() { + a, b, c := 2, foo() + + println(a, b, c) +} + +// Error: +// main/files/assign25.gno:8:2: assignment mismatch: 3 variable(s) but 2 value(s) diff --git a/gnovm/tests/files/assign25b.gno b/gnovm/tests/files/assign25b.gno new file mode 100644 index 00000000000..886777324f5 --- /dev/null +++ b/gnovm/tests/files/assign25b.gno @@ -0,0 +1,14 @@ +package main + +func foo() (int, bool) { + return 1, true +} + +func main() { + a, b, c := 2, 3, 4, foo() + + println(a, b, c) +} + +// Error: +// main/files/assign25b.gno:8:2: assignment mismatch: 3 variable(s) but 4 value(s) diff --git a/gnovm/tests/files/assign26.gno b/gnovm/tests/files/assign26.gno new file mode 100644 index 00000000000..f974ae0b174 --- /dev/null +++ b/gnovm/tests/files/assign26.gno @@ -0,0 +1,9 @@ +package main + +func main() { + var i interface{} = 1 + a, b, c := i.(int) +} + +// Error: +// main/files/assign26.gno:5:2: assignment mismatch: 3 variable(s) but 1 value(s) diff --git a/gnovm/tests/files/assign27.gno b/gnovm/tests/files/assign27.gno new file mode 100644 index 00000000000..14fc8bf4e37 --- /dev/null +++ b/gnovm/tests/files/assign27.gno @@ -0,0 +1,9 @@ +package main + +func main() { + s := []string{"1", "2"} + a, b, c := s[0] +} + +// Error: +// main/files/assign27.gno:5:2: assignment mismatch: 3 variable(s) but 1 value(s) diff --git a/gnovm/tests/files/assign28.gno b/gnovm/tests/files/assign28.gno new file mode 100644 index 00000000000..a0afe4f0e36 --- /dev/null +++ b/gnovm/tests/files/assign28.gno @@ -0,0 +1,11 @@ +package main + +import "fmt" + +func main() { + a, c := 1, 2, 3 + fmt.Println(a, c) +} + +// Error: +// main/files/assign28.gno:6:2: assignment mismatch: 2 variable(s) but 3 value(s) diff --git a/gnovm/tests/files/var18.gno b/gnovm/tests/files/var18.gno index 771ddcdffb5..f01d3871d39 100644 --- a/gnovm/tests/files/var18.gno +++ b/gnovm/tests/files/var18.gno @@ -1,8 +1,8 @@ package main func main() { - a, b, c := 1, 2 + var a, b, c = 1, 2 } // Error: -// main/files/var18.gno:4:2: assignment mismatch: 3 variables but 2 values +// main/files/var18.gno:4:6: missing init expr for c diff --git a/gnovm/tests/files/var19.gno b/gnovm/tests/files/var19.gno new file mode 100644 index 00000000000..cbdce802e0a --- /dev/null +++ b/gnovm/tests/files/var19.gno @@ -0,0 +1,11 @@ +package main + +func main() { + var a, b, c = 1, a+1 + println(a) + println(b) + println(c) +} + +// Error: +// main/files/var19.gno:4:6: missing init expr for c diff --git a/gnovm/tests/files/var20.gno b/gnovm/tests/files/var20.gno new file mode 100644 index 00000000000..e2455cbaed8 --- /dev/null +++ b/gnovm/tests/files/var20.gno @@ -0,0 +1,12 @@ +package main + +func r() int { + return 1 +} + +func main() { + var a, b, c = r() +} + +// Error: +// main/files/var20.gno:8:6: assignment mismatch: 3 variable(s) but r returns 1 value(s) diff --git a/gnovm/tests/files/var21.gno b/gnovm/tests/files/var21.gno new file mode 100644 index 00000000000..b593984aa87 --- /dev/null +++ b/gnovm/tests/files/var21.gno @@ -0,0 +1,14 @@ +package main + +func foo() (int, bool) { + return 1, true +} + +func main() { + var a, b = 2, foo() + + println(a, b) +} + +// Error: +// main/files/var21.gno:8:6: multiple-value foo (value of type [int bool]) in single-value context diff --git a/gnovm/tests/files/var22.gno b/gnovm/tests/files/var22.gno new file mode 100644 index 00000000000..3f85f0f156d --- /dev/null +++ b/gnovm/tests/files/var22.gno @@ -0,0 +1,14 @@ +package main + +func foo() (int, bool) { + return 1, true +} + +func main() { + var a, b, c = 2, foo() + + println(a, b, c) +} + +// Error: +// main/files/var22.gno:8:6: missing init expr for c diff --git a/gnovm/tests/files/var22b.gno b/gnovm/tests/files/var22b.gno new file mode 100644 index 00000000000..22a52fcc811 --- /dev/null +++ b/gnovm/tests/files/var22b.gno @@ -0,0 +1,14 @@ +package main + +func foo() (int, bool) { + return 1, true +} + +func main() { + var a, b, c = 2, 3, 4, foo() + + println(a, b, c) +} + +// Error: +// main/files/var22b.gno:8:6: extra init expr foo() diff --git a/gnovm/tests/files/var23.gno b/gnovm/tests/files/var23.gno new file mode 100644 index 00000000000..b9f98311411 --- /dev/null +++ b/gnovm/tests/files/var23.gno @@ -0,0 +1,9 @@ +package main + +var a, b, c = 1, 2 + +func main() { +} + +// Error: +// main/files/var23.gno:3:5: assignment mismatch: 3 variable(s) but 2 value(s) diff --git a/gnovm/tests/files/var24.gno b/gnovm/tests/files/var24.gno new file mode 100644 index 00000000000..ddfa82a1e4e --- /dev/null +++ b/gnovm/tests/files/var24.gno @@ -0,0 +1,9 @@ +package main + +func main() { + var i interface{} = 1 + var a, b, c = i.(int) +} + +// Error: +// main/files/var24.gno:5:6: assignment mismatch: 3 variable(s) but 1 value(s) diff --git a/gnovm/tests/files/var25.gno b/gnovm/tests/files/var25.gno new file mode 100644 index 00000000000..999979dcf71 --- /dev/null +++ b/gnovm/tests/files/var25.gno @@ -0,0 +1,9 @@ +package main + +func main() { + s := []string{"1", "2"} + var a, b, c = s[0] +} + +// Error: +// main/files/var25.gno:5:6: assignment mismatch: 3 variable(s) but 1 value(s) diff --git a/gnovm/tests/files/var26.gno b/gnovm/tests/files/var26.gno new file mode 100644 index 00000000000..71b6f3a4eb0 --- /dev/null +++ b/gnovm/tests/files/var26.gno @@ -0,0 +1,11 @@ +package main + +import "fmt" + +func main() { + var a, c = 1, 2, 3 + fmt.Println(a, c) +} + +// Error: +// main/files/var26.gno:6:6: extra init expr 3 From d9925bfb4c9d137ebc9239046b4edb1d246354c0 Mon Sep 17 00:00:00 2001 From: Jeff Thompson Date: Tue, 30 Jul 2024 19:14:28 +0200 Subject: [PATCH 2/7] fix(r/demo/profile): in fieldHandler, escape bio with `url.QueryEscape` (#2642) In r/demo/profile, if the Bio field is "My bio", then the web render for `r/demo/profile:f/g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5/Bio` shows: ``` Bio: My bio [Edit](/r/demo/profile?help&__func=SetStringField&field=Bio&addr=g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5&value=My bio) ``` The `[Edit]` link doesn't display properly because of the space in "My bio". This PR updates fieldHandler to use `url.QueryEscape`. With this fix the web render is as expected with the correct `[Edit]` link: ``` Bio: My bio Edit ``` Signed-off-by: Jeff Thompson --- examples/gno.land/r/demo/profile/render.gno | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/examples/gno.land/r/demo/profile/render.gno b/examples/gno.land/r/demo/profile/render.gno index 4ff295e65eb..79d1078a997 100644 --- a/examples/gno.land/r/demo/profile/render.gno +++ b/examples/gno.land/r/demo/profile/render.gno @@ -2,6 +2,7 @@ package profile import ( "bytes" + "net/url" "std" "gno.land/p/demo/mux" @@ -83,7 +84,7 @@ func fieldHandler(res *mux.ResponseWriter, req *mux.Request) { if _, ok := stringFields[field]; ok { value = ufmt.Sprintf("%s", GetStringField(address, field, "n/a")) - editLink = ufmt.Sprintf(SetStringFieldURL+"&addr=%s&value=%s", field, addr, value) + editLink = ufmt.Sprintf(SetStringFieldURL+"&addr=%s&value=%s", field, addr, url.QueryEscape(value)) } else if _, ok := intFields[field]; ok { value = ufmt.Sprintf("%d", GetIntField(address, field, 0)) editLink = ufmt.Sprintf(SetIntFieldURL+"&addr=%s&value=%s", field, addr, value) From 9b114172063feaf2da4ae7ebb8263cada3ba699b Mon Sep 17 00:00:00 2001 From: Guilhem Fanton <8671905+gfanton@users.noreply.github.com> Date: Tue, 30 Jul 2024 19:15:06 +0200 Subject: [PATCH 3/7] fix(fmt): do not print a second line when printing file to stdout (#2639) closes #2633 Avoid double printing newline when executing `gno fmt` without the `-w` (write) flag. --------- Signed-off-by: gfanton <8671905+gfanton@users.noreply.github.com> --- gnovm/cmd/gno/fmt.go | 2 +- gnovm/cmd/gno/testdata/gno_fmt/empty.txtar | 1 - gnovm/cmd/gno/testdata/gno_fmt/import_cleaning.txtar | 1 - gnovm/cmd/gno/testdata/gno_fmt/include.txtar | 1 - gnovm/cmd/gno/testdata/gno_fmt/multi_import.txtar | 1 - gnovm/cmd/gno/testdata/gno_fmt/noimport_format.txtar | 1 - gnovm/cmd/gno/testdata/gno_fmt/shadow_import.txtar | 1 - 7 files changed, 1 insertion(+), 7 deletions(-) diff --git a/gnovm/cmd/gno/fmt.go b/gnovm/cmd/gno/fmt.go index 7c5ad42c2b0..de6c28c4df0 100644 --- a/gnovm/cmd/gno/fmt.go +++ b/gnovm/cmd/gno/fmt.go @@ -162,7 +162,7 @@ func fmtProcessSingleFile(cfg *fmtCfg, file string, processFile fmtProcessFileFu } if !cfg.write { if !cfg.diff && !cfg.quiet { - io.Println(string(out)) + io.Out().Write(out) } return true } diff --git a/gnovm/cmd/gno/testdata/gno_fmt/empty.txtar b/gnovm/cmd/gno/testdata/gno_fmt/empty.txtar index 14f85227335..97d367f6fdb 100644 --- a/gnovm/cmd/gno/testdata/gno_fmt/empty.txtar +++ b/gnovm/cmd/gno/testdata/gno_fmt/empty.txtar @@ -6,5 +6,4 @@ cmp stderr stderr.golden package hello -- stdout.golden.gno -- package hello - -- stderr.golden -- diff --git a/gnovm/cmd/gno/testdata/gno_fmt/import_cleaning.txtar b/gnovm/cmd/gno/testdata/gno_fmt/import_cleaning.txtar index bc186f98b6f..3d50f4e6428 100644 --- a/gnovm/cmd/gno/testdata/gno_fmt/import_cleaning.txtar +++ b/gnovm/cmd/gno/testdata/gno_fmt/import_cleaning.txtar @@ -26,5 +26,4 @@ var rand = &S{} package testdata var yes = rand.Val - -- stderr.golden -- diff --git a/gnovm/cmd/gno/testdata/gno_fmt/include.txtar b/gnovm/cmd/gno/testdata/gno_fmt/include.txtar index 92767983705..1cfedd06ad4 100644 --- a/gnovm/cmd/gno/testdata/gno_fmt/include.txtar +++ b/gnovm/cmd/gno/testdata/gno_fmt/include.txtar @@ -27,5 +27,4 @@ package testdata import "gno.land/r/test/mypkg" var myVar = mypkg.HelloFromMyPkg() - -- stderr.golden -- diff --git a/gnovm/cmd/gno/testdata/gno_fmt/multi_import.txtar b/gnovm/cmd/gno/testdata/gno_fmt/multi_import.txtar index 9e16f33591d..4002902bc59 100644 --- a/gnovm/cmd/gno/testdata/gno_fmt/multi_import.txtar +++ b/gnovm/cmd/gno/testdata/gno_fmt/multi_import.txtar @@ -92,5 +92,4 @@ func myBlog() *blog.Blog { return &blog.Blog{} } - -- stderr.golden -- diff --git a/gnovm/cmd/gno/testdata/gno_fmt/noimport_format.txtar b/gnovm/cmd/gno/testdata/gno_fmt/noimport_format.txtar index 56fca6ddbd7..6470fe76297 100644 --- a/gnovm/cmd/gno/testdata/gno_fmt/noimport_format.txtar +++ b/gnovm/cmd/gno/testdata/gno_fmt/noimport_format.txtar @@ -35,5 +35,4 @@ import ( ) var yes = rand.Val - -- stderr.golden -- diff --git a/gnovm/cmd/gno/testdata/gno_fmt/shadow_import.txtar b/gnovm/cmd/gno/testdata/gno_fmt/shadow_import.txtar index 50d0970497e..19ad27b2f1a 100644 --- a/gnovm/cmd/gno/testdata/gno_fmt/shadow_import.txtar +++ b/gnovm/cmd/gno/testdata/gno_fmt/shadow_import.txtar @@ -49,5 +49,4 @@ import ( func main() { println("a", v1.Get("a")) } - -- stderr.golden -- From 879c4b60875e801b9b308e748fb35a57680b3b85 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 30 Jul 2024 19:42:57 +0200 Subject: [PATCH 4/7] chore(deps): bump the everything-else group across 1 directory with 5 updates (#2612) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Bumps the everything-else group with 5 updates in the / directory: | Package | From | To | | --- | --- | --- | | [github.com/btcsuite/btcd/btcec/v2](https://github.com/btcsuite/btcd) | `2.3.3` | `2.3.4` | | [github.com/gorilla/websocket](https://github.com/gorilla/websocket) | `1.5.1` | `1.5.3` | | [github.com/mattn/go-runewidth](https://github.com/mattn/go-runewidth) | `0.0.15` | `0.0.16` | | [go.etcd.io/bbolt](https://github.com/etcd-io/bbolt) | `1.3.9` | `1.3.10` | | [golang.org/x/tools](https://github.com/golang/tools) | `0.22.0` | `0.23.0` | Updates `github.com/btcsuite/btcd/btcec/v2` from 2.3.3 to 2.3.4
Commits
  • ff2e03e chore: fix some comments for struct field (#2214)
  • 2134387 Merge pull request #2208 from kcalvinalvin/2024-07-01-close-blockfiles
  • e5d15fd btcec/ecdsa: remove error return value for SignCompact (#2211)
  • c9fae1a ffldb: close block files before deleting them
  • 8ed8ef1 ffldb: refactor out file close code into its own method
  • 8b5f2aa ffldb: add check for deleting files that are open
  • 4712e20 ffldb: throw error when attempting to delete an open file
  • d881c68 Fix the btcctl uptime command
  • 1396690 Sending RPC requests through unix sockets (#2168)
  • b2eec96 Merge pull request #2206 from guggero/psbt-serialization-fix
  • Additional commits viewable in compare view

Updates `github.com/gorilla/websocket` from 1.5.1 to 1.5.3
Release notes

Sourced from github.com/gorilla/websocket's releases.

v1.5.3

Important change

This reverts the websockets package back to https://github.com/gorilla/websocket/commit/931041c5ee6de24fe9cba1aa16f1a0b910284d6d

What's Changed

New Contributors

Full Changelog: https://github.com/gorilla/websocket/compare/v1.5.1...v1.5.3

v1.5.2

What's Changed

... (truncated)

Commits
  • ce903f6 Reverts to v1.5.0
  • 9ec25ca fixes broken random value generation
  • 1bddf2e bumps go version & removes deprecated module usage
  • 750bf92 adds GHA & Makefile configs
  • b2c246b Revert " Update go version & add verification/testing tools (#840)"
  • 09a6bab removing error handling while closing connections
  • 58af150 return errors instead of printing to logs
  • e5f1a0a excludes errchecks linter
  • b2a86a1 Do not timeout when WriteControl deadline is zero
  • 695e909 Remove hideTempErr to allow downstream users to check for errors like net.Err...
  • Additional commits viewable in compare view

Updates `github.com/mattn/go-runewidth` from 0.0.15 to 0.0.16
Commits

Updates `go.etcd.io/bbolt` from 1.3.9 to 1.3.10
Release notes

Sourced from go.etcd.io/bbolt's releases.

v1.3.10

See the CHANGELOG for more details.

Commits
  • 014b028 Merge pull request #744 from ahrtr/cursor_20240502
  • 2d48e1d Ensure a cursor can continue to iterate elements in reverse direction by call...
  • 886753c Merge pull request #717 from henrybear327/fix/remove_UnsafeSlice
  • 9e3d732 Remove UnsafeSlice and use unsafe.Slice
  • 2c29534 Merge pull request #713 from henrybear327/cve/CVE-2023-45288-release-1.3
  • 9b60c13 Address linter issues
  • 0b59bc1 Bump go toolchain version to address CVE-2023-45288
  • 9f3524b Merge pull request #716 from henrybear327/feat/introduce-go-version-file
  • 67a2678 Adopt the .go-version approach for toolchain versioning
  • See full diff in compare view

Updates `golang.org/x/tools` from 0.22.0 to 0.23.0
Commits
  • 33be3ef go.mod: update golang.org/x dependencies
  • 0e7ccc0 gopls/internal/golang: provide version info for stdlib in pkgdoc
  • fcf5463 gopls/internal/server: add counters to inform v0.17.0
  • 70a59b2 gopls/doc: respond to Hana's review of CL 583316
  • 799a471 gopls/doc: document all of gopls' features
  • 2e239ad gopls/internal/golang: provide version info for stdlib fields
  • bc15dd8 gopls/internal/analysis/fillstruct: use package name (not path) in UI
  • 72edac2 internal/typeparams: fix crash in interface hover with empty type set
  • c0ae6bb gopls/internal/golang: splitlines: s/parameter/arguments/ in CallExpr
  • 5cc2d0b gopls/internal/golang: splitlines: remove workaround for golang/go#68202
  • Additional commits viewable in compare view

Dependabot will resolve any conflicts with this PR as long as you don't alter it yourself. You can also trigger a rebase manually by commenting `@dependabot rebase`. [//]: # (dependabot-automerge-start) [//]: # (dependabot-automerge-end) ---
Dependabot commands and options
You can trigger Dependabot actions by commenting on this PR: - `@dependabot rebase` will rebase this PR - `@dependabot recreate` will recreate this PR, overwriting any edits that have been made to it - `@dependabot merge` will merge this PR after your CI passes on it - `@dependabot squash and merge` will squash and merge this PR after your CI passes on it - `@dependabot cancel merge` will cancel a previously requested merge and block automerging - `@dependabot reopen` will reopen this PR if it is closed - `@dependabot close` will close this PR and stop Dependabot recreating it. You can achieve the same result by closing it manually - `@dependabot show ignore conditions` will show all of the ignore conditions of the specified dependency - `@dependabot ignore major version` will close this group update PR and stop Dependabot creating any more for the specific dependency's major version (unless you unignore this specific dependency's major version or upgrade to it yourself) - `@dependabot ignore minor version` will close this group update PR and stop Dependabot creating any more for the specific dependency's minor version (unless you unignore this specific dependency's minor version or upgrade to it yourself) - `@dependabot ignore ` will close this group update PR and stop Dependabot creating any more for the specific dependency (unless you unignore this specific dependency or upgrade to it yourself) - `@dependabot unignore ` will remove all of the ignore conditions of the specified dependency - `@dependabot unignore ` will remove the ignore condition of the specified dependency and ignore conditions
--------- Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: dependabot[bot] --- contribs/gnodev/go.mod | 10 +++++----- contribs/gnodev/go.sum | 20 ++++++++++---------- contribs/gnokeykc/go.mod | 4 ++-- contribs/gnokeykc/go.sum | 12 ++++++------ go.mod | 10 +++++----- go.sum | 19 ++++++++++--------- 6 files changed, 38 insertions(+), 37 deletions(-) diff --git a/contribs/gnodev/go.mod b/contribs/gnodev/go.mod index 77631a0190f..53973b15fbf 100644 --- a/contribs/gnodev/go.mod +++ b/contribs/gnodev/go.mod @@ -11,7 +11,7 @@ require ( github.com/charmbracelet/log v0.3.1 github.com/fsnotify/fsnotify v1.7.0 github.com/gnolang/gno v0.0.0-00010101000000-000000000000 - github.com/gorilla/websocket v1.5.1 + github.com/gorilla/websocket v1.5.3 github.com/muesli/termenv v0.15.2 github.com/stretchr/testify v1.9.0 go.uber.org/zap v1.27.0 @@ -21,7 +21,7 @@ require ( require ( dario.cat/mergo v1.0.0 // indirect github.com/aymanbagabas/go-osc52/v2 v2.0.1 // indirect - github.com/btcsuite/btcd/btcec/v2 v2.3.3 // indirect + github.com/btcsuite/btcd/btcec/v2 v2.3.4 // indirect github.com/btcsuite/btcd/btcutil v1.1.5 // indirect github.com/cenkalti/backoff/v4 v4.3.0 // indirect github.com/cockroachdb/apd/v3 v3.2.1 // indirect @@ -43,7 +43,7 @@ require ( github.com/libp2p/go-buffer-pool v0.1.0 // indirect github.com/lucasb-eyer/go-colorful v1.2.0 // indirect github.com/mattn/go-isatty v0.0.18 // indirect - github.com/mattn/go-runewidth v0.0.15 // indirect + github.com/mattn/go-runewidth v0.0.16 // indirect github.com/muesli/reflow v0.3.0 // indirect github.com/pelletier/go-toml v1.9.5 // indirect github.com/peterbourgon/ff/v3 v3.4.0 // indirect @@ -56,7 +56,7 @@ require ( github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 // indirect github.com/zondax/hid v0.9.2 // indirect github.com/zondax/ledger-go v0.14.3 // indirect - go.etcd.io/bbolt v1.3.9 // indirect + go.etcd.io/bbolt v1.3.10 // indirect go.opentelemetry.io/otel v1.28.0 // indirect go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetricgrpc v1.28.0 // indirect go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetrichttp v1.28.0 // indirect @@ -73,7 +73,7 @@ require ( golang.org/x/net v0.27.0 // indirect golang.org/x/sys v0.22.0 // indirect golang.org/x/text v0.16.0 // indirect - golang.org/x/tools v0.22.0 // indirect + golang.org/x/tools v0.23.0 // indirect google.golang.org/genproto/googleapis/api v0.0.0-20240701130421-f6361c86f094 // indirect google.golang.org/genproto/googleapis/rpc v0.0.0-20240701130421-f6361c86f094 // indirect google.golang.org/grpc v1.65.0 // indirect diff --git a/contribs/gnodev/go.sum b/contribs/gnodev/go.sum index f4eb9423c21..2b5c964a014 100644 --- a/contribs/gnodev/go.sum +++ b/contribs/gnodev/go.sum @@ -9,8 +9,8 @@ github.com/btcsuite/btcd v0.23.5-0.20231215221805-96c9fd8078fd h1:js1gPwhcFflTZ7 github.com/btcsuite/btcd v0.23.5-0.20231215221805-96c9fd8078fd/go.mod h1:nm3Bko6zh6bWP60UxwoT5LzdGJsQJaPo6HjduXq9p6A= github.com/btcsuite/btcd/btcec/v2 v2.1.0/go.mod h1:2VzYrv4Gm4apmbVVsSq5bqf1Ec8v56E48Vt0Y/umPgA= github.com/btcsuite/btcd/btcec/v2 v2.1.3/go.mod h1:ctjw4H1kknNJmRN4iP1R7bTQ+v3GJkZBd6mui8ZsAZE= -github.com/btcsuite/btcd/btcec/v2 v2.3.3 h1:6+iXlDKE8RMtKsvK0gshlXIuPbyWM/h84Ensb7o3sC0= -github.com/btcsuite/btcd/btcec/v2 v2.3.3/go.mod h1:zYzJ8etWJQIv1Ogk7OzpWjowwOdXY1W/17j2MW85J04= +github.com/btcsuite/btcd/btcec/v2 v2.3.4 h1:3EJjcN70HCu/mwqlUsGK8GcNVyLVxFDlWurTXGPFfiQ= +github.com/btcsuite/btcd/btcec/v2 v2.3.4/go.mod h1:zYzJ8etWJQIv1Ogk7OzpWjowwOdXY1W/17j2MW85J04= github.com/btcsuite/btcd/btcutil v1.0.0/go.mod h1:Uoxwv0pqYWhD//tfTiipkxNfdhG9UrLwaeswfjfdF0A= github.com/btcsuite/btcd/btcutil v1.1.0/go.mod h1:5OapHB7A2hBBWLm48mmw4MOHNJCcUBTwmWH/0Jn8VHE= github.com/btcsuite/btcd/btcutil v1.1.5 h1:+wER79R5670vs/ZusMTF1yTcRYE5GUsFbdjdisflzM8= @@ -93,8 +93,8 @@ github.com/gorilla/securecookie v1.1.1/go.mod h1:ra0sb63/xPlUeL+yeDciTfxMRAA+MP+ github.com/gorilla/sessions v1.2.1 h1:DHd3rPN5lE3Ts3D8rKkQ8x/0kqfeNmBAaiSi+o7FsgI= github.com/gorilla/sessions v1.2.1/go.mod h1:dk2InVEVJ0sfLlnXv9EAgkf6ecYs/i80K/zI+bUmuGM= github.com/gorilla/websocket v1.5.0/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= -github.com/gorilla/websocket v1.5.1 h1:gmztn0JnHVt9JZquRuzLw3g4wouNVzKL15iLr/zn/QY= -github.com/gorilla/websocket v1.5.1/go.mod h1:x3kM2JMyaluk02fnUJpQuwD2dCS5NDG2ZHL0uE0tcaY= +github.com/gorilla/websocket v1.5.3 h1:saDtZ6Pbx/0u+bgYQ3q96pZgCzfhKXGPqt7kZ72aNNg= +github.com/gorilla/websocket v1.5.3/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= github.com/gotuna/gotuna v0.6.0 h1:N1lQKXEi/lwRp8u3sccTYLhzOffA4QasExz/1M5Riws= github.com/gotuna/gotuna v0.6.0/go.mod h1:F/ecRt29ChB6Ycy1AFIBpBiMNK0j7Heq+gFbLWquhjc= github.com/grpc-ecosystem/grpc-gateway/v2 v2.20.0 h1:bkypFPDjIYGfCYD5mRBvpqxfYX1YCS1PXdKYWi8FsN0= @@ -117,8 +117,8 @@ github.com/lucasb-eyer/go-colorful v1.2.0/go.mod h1:R4dSotOR9KMtayYi1e77YzuveK+i github.com/mattn/go-isatty v0.0.18 h1:DOKFKCQ7FNG2L1rbrmstDN4QVRdS89Nkh85u68Uwp98= github.com/mattn/go-isatty v0.0.18/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y= github.com/mattn/go-runewidth v0.0.12/go.mod h1:RAqKPSqVFrSLVXbA8x7dzmKdmGzieGRCM46jaSJTDAk= -github.com/mattn/go-runewidth v0.0.15 h1:UNAjwbU9l54TA3KzvqLGxwWjHmMgBUVhBiTjelZgg3U= -github.com/mattn/go-runewidth v0.0.15/go.mod h1:Jdepj2loyihRzMpdS35Xk/zdY8IAYHsh153qUoGf23w= +github.com/mattn/go-runewidth v0.0.16 h1:E5ScNMtiwvlvB5paMFdw9p4kSQzbXFikJ5SQO6TULQc= +github.com/mattn/go-runewidth v0.0.16/go.mod h1:Jdepj2loyihRzMpdS35Xk/zdY8IAYHsh153qUoGf23w= github.com/muesli/reflow v0.3.0 h1:IFsN6K9NfGtjeggFP+68I4chLZV2yIKsXJFNZ+eWh6s= github.com/muesli/reflow v0.3.0/go.mod h1:pbwTDkVPibjO2kyvBQRBxTWEEGDGq0FlB1BIKtnHY/8= github.com/muesli/termenv v0.15.2 h1:GohcuySI0QmI3wN8Ok9PtKGkgkFIk7y6Vpb5PvrY+Wo= @@ -164,8 +164,8 @@ github.com/zondax/hid v0.9.2 h1:WCJFnEDMiqGF64nlZz28E9qLVZ0KSJ7xpc5DLEyma2U= github.com/zondax/hid v0.9.2/go.mod h1:l5wttcP0jwtdLjqjMMWFVEE7d1zO0jvSPA9OPZxWpEM= github.com/zondax/ledger-go v0.14.3 h1:wEpJt2CEcBJ428md/5MgSLsXLBos98sBOyxNmCjfUCw= github.com/zondax/ledger-go v0.14.3/go.mod h1:IKKaoxupuB43g4NxeQmbLXv7T9AlQyie1UpHb342ycI= -go.etcd.io/bbolt v1.3.9 h1:8x7aARPEXiXbHmtUwAIv7eV2fQFHrLLavdiJ3uzJXoI= -go.etcd.io/bbolt v1.3.9/go.mod h1:zaO32+Ti0PK1ivdPtgMESzuzL2VPoIG1PCQNvOdo/dE= +go.etcd.io/bbolt v1.3.10 h1:+BqfJTcCzTItrop8mq/lbzL8wSGtj94UO/3U31shqG0= +go.etcd.io/bbolt v1.3.10/go.mod h1:bK3UQLPJZly7IlNmV7uVHJDxfe5aK9Ll93e/74Y9oEQ= go.opentelemetry.io/otel v1.28.0 h1:/SqNcYk+idO0CxKEUOtKQClMK/MimZihKYMruSMViUo= go.opentelemetry.io/otel v1.28.0/go.mod h1:q68ijF8Fc8CnMHKyzqL6akLO46ePnjkgfIMIjUIX9z4= go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetricgrpc v1.28.0 h1:U2guen0GhqH8o/G2un8f/aG/y++OuW6MyCo6hT9prXk= @@ -229,8 +229,8 @@ golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.16.0 h1:a94ExnEXNtEwYLGJSIUxnWoxoRz/ZcCsV63ROupILh4= golang.org/x/text v0.16.0/go.mod h1:GhwF1Be+LQoKShO3cGOHzqOgRrGaYc9AvblQOmPVHnI= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= -golang.org/x/tools v0.22.0 h1:gqSGLZqv+AI9lIQzniJ0nZDRG5GBPsSi+DRNHWNz6yA= -golang.org/x/tools v0.22.0/go.mod h1:aCwcsjqvq7Yqt6TNyX7QMU2enbQ/Gt0bo6krSeEri+c= +golang.org/x/tools v0.23.0 h1:SGsXPZ+2l4JsgaCKkx+FQ9YZ5XEtA1GZYuoDjenLjvg= +golang.org/x/tools v0.23.0/go.mod h1:pnu6ufv6vQkll6szChhK3C3L/ruaIv5eBeztNG8wtsI= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE= golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= diff --git a/contribs/gnokeykc/go.mod b/contribs/gnokeykc/go.mod index d86c71558fb..9531b94a628 100644 --- a/contribs/gnokeykc/go.mod +++ b/contribs/gnokeykc/go.mod @@ -13,7 +13,7 @@ require ( require ( github.com/alessio/shellescape v1.4.1 // indirect - github.com/btcsuite/btcd/btcec/v2 v2.3.3 // indirect + github.com/btcsuite/btcd/btcec/v2 v2.3.4 // indirect github.com/btcsuite/btcd/btcutil v1.1.5 // indirect github.com/cenkalti/backoff/v4 v4.3.0 // indirect github.com/cockroachdb/apd/v3 v3.2.1 // indirect @@ -28,7 +28,7 @@ require ( github.com/golang/protobuf v1.5.4 // indirect github.com/golang/snappy v0.0.4 // indirect github.com/google/uuid v1.6.0 // indirect - github.com/gorilla/websocket v1.5.1 // indirect + github.com/gorilla/websocket v1.5.3 // indirect github.com/grpc-ecosystem/grpc-gateway/v2 v2.20.0 // indirect github.com/libp2p/go-buffer-pool v0.1.0 // indirect github.com/pelletier/go-toml v1.9.5 // indirect diff --git a/contribs/gnokeykc/go.sum b/contribs/gnokeykc/go.sum index e20600ea557..20c847e59f8 100644 --- a/contribs/gnokeykc/go.sum +++ b/contribs/gnokeykc/go.sum @@ -9,8 +9,8 @@ github.com/btcsuite/btcd v0.23.5-0.20231215221805-96c9fd8078fd h1:js1gPwhcFflTZ7 github.com/btcsuite/btcd v0.23.5-0.20231215221805-96c9fd8078fd/go.mod h1:nm3Bko6zh6bWP60UxwoT5LzdGJsQJaPo6HjduXq9p6A= github.com/btcsuite/btcd/btcec/v2 v2.1.0/go.mod h1:2VzYrv4Gm4apmbVVsSq5bqf1Ec8v56E48Vt0Y/umPgA= github.com/btcsuite/btcd/btcec/v2 v2.1.3/go.mod h1:ctjw4H1kknNJmRN4iP1R7bTQ+v3GJkZBd6mui8ZsAZE= -github.com/btcsuite/btcd/btcec/v2 v2.3.3 h1:6+iXlDKE8RMtKsvK0gshlXIuPbyWM/h84Ensb7o3sC0= -github.com/btcsuite/btcd/btcec/v2 v2.3.3/go.mod h1:zYzJ8etWJQIv1Ogk7OzpWjowwOdXY1W/17j2MW85J04= +github.com/btcsuite/btcd/btcec/v2 v2.3.4 h1:3EJjcN70HCu/mwqlUsGK8GcNVyLVxFDlWurTXGPFfiQ= +github.com/btcsuite/btcd/btcec/v2 v2.3.4/go.mod h1:zYzJ8etWJQIv1Ogk7OzpWjowwOdXY1W/17j2MW85J04= github.com/btcsuite/btcd/btcutil v1.0.0/go.mod h1:Uoxwv0pqYWhD//tfTiipkxNfdhG9UrLwaeswfjfdF0A= github.com/btcsuite/btcd/btcutil v1.1.0/go.mod h1:5OapHB7A2hBBWLm48mmw4MOHNJCcUBTwmWH/0Jn8VHE= github.com/btcsuite/btcd/btcutil v1.1.5 h1:+wER79R5670vs/ZusMTF1yTcRYE5GUsFbdjdisflzM8= @@ -82,8 +82,8 @@ github.com/google/gofuzz v1.2.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/ github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0= github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/gorilla/websocket v1.5.0/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= -github.com/gorilla/websocket v1.5.1 h1:gmztn0JnHVt9JZquRuzLw3g4wouNVzKL15iLr/zn/QY= -github.com/gorilla/websocket v1.5.1/go.mod h1:x3kM2JMyaluk02fnUJpQuwD2dCS5NDG2ZHL0uE0tcaY= +github.com/gorilla/websocket v1.5.3 h1:saDtZ6Pbx/0u+bgYQ3q96pZgCzfhKXGPqt7kZ72aNNg= +github.com/gorilla/websocket v1.5.3/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= github.com/grpc-ecosystem/grpc-gateway/v2 v2.20.0 h1:bkypFPDjIYGfCYD5mRBvpqxfYX1YCS1PXdKYWi8FsN0= github.com/grpc-ecosystem/grpc-gateway/v2 v2.20.0/go.mod h1:P+Lt/0by1T8bfcF3z737NnSbmxQAppXMRziHUxPOC8k= github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU= @@ -138,8 +138,8 @@ github.com/zondax/hid v0.9.2 h1:WCJFnEDMiqGF64nlZz28E9qLVZ0KSJ7xpc5DLEyma2U= github.com/zondax/hid v0.9.2/go.mod h1:l5wttcP0jwtdLjqjMMWFVEE7d1zO0jvSPA9OPZxWpEM= github.com/zondax/ledger-go v0.14.3 h1:wEpJt2CEcBJ428md/5MgSLsXLBos98sBOyxNmCjfUCw= github.com/zondax/ledger-go v0.14.3/go.mod h1:IKKaoxupuB43g4NxeQmbLXv7T9AlQyie1UpHb342ycI= -go.etcd.io/bbolt v1.3.9 h1:8x7aARPEXiXbHmtUwAIv7eV2fQFHrLLavdiJ3uzJXoI= -go.etcd.io/bbolt v1.3.9/go.mod h1:zaO32+Ti0PK1ivdPtgMESzuzL2VPoIG1PCQNvOdo/dE= +go.etcd.io/bbolt v1.3.10 h1:+BqfJTcCzTItrop8mq/lbzL8wSGtj94UO/3U31shqG0= +go.etcd.io/bbolt v1.3.10/go.mod h1:bK3UQLPJZly7IlNmV7uVHJDxfe5aK9Ll93e/74Y9oEQ= go.opentelemetry.io/otel v1.28.0 h1:/SqNcYk+idO0CxKEUOtKQClMK/MimZihKYMruSMViUo= go.opentelemetry.io/otel v1.28.0/go.mod h1:q68ijF8Fc8CnMHKyzqL6akLO46ePnjkgfIMIjUIX9z4= go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetricgrpc v1.28.0 h1:U2guen0GhqH8o/G2un8f/aG/y++OuW6MyCo6hT9prXk= diff --git a/go.mod b/go.mod index c155a23f16b..d0845d73641 100644 --- a/go.mod +++ b/go.mod @@ -6,7 +6,7 @@ toolchain go1.22.4 require ( dario.cat/mergo v1.0.0 - github.com/btcsuite/btcd/btcec/v2 v2.3.3 + github.com/btcsuite/btcd/btcec/v2 v2.3.4 github.com/btcsuite/btcd/btcutil v1.1.5 github.com/cockroachdb/apd/v3 v3.2.1 github.com/cosmos/ledger-cosmos-go v0.13.3 @@ -18,10 +18,10 @@ require ( github.com/golang/protobuf v1.5.4 github.com/google/gofuzz v1.2.0 github.com/gorilla/mux v1.8.1 - github.com/gorilla/websocket v1.5.1 + github.com/gorilla/websocket v1.5.3 github.com/gotuna/gotuna v0.6.0 github.com/libp2p/go-buffer-pool v0.1.0 - github.com/mattn/go-runewidth v0.0.15 + github.com/mattn/go-runewidth v0.0.16 github.com/pelletier/go-toml v1.9.5 github.com/peterbourgon/ff/v3 v3.4.0 github.com/pmezard/go-difflib v1.0.0 @@ -30,7 +30,7 @@ require ( github.com/rs/xid v1.5.0 github.com/stretchr/testify v1.9.0 github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 - go.etcd.io/bbolt v1.3.9 + go.etcd.io/bbolt v1.3.10 go.opentelemetry.io/otel v1.28.0 go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetricgrpc v1.28.0 go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetrichttp v1.28.0 @@ -46,7 +46,7 @@ require ( golang.org/x/net v0.27.0 golang.org/x/sync v0.7.0 golang.org/x/term v0.22.0 - golang.org/x/tools v0.22.0 + golang.org/x/tools v0.23.0 google.golang.org/protobuf v1.34.2 gopkg.in/yaml.v3 v3.0.1 ) diff --git a/go.sum b/go.sum index 9fde89e8cec..5cb6be26da2 100644 --- a/go.sum +++ b/go.sum @@ -7,8 +7,8 @@ github.com/btcsuite/btcd v0.23.5-0.20231215221805-96c9fd8078fd h1:js1gPwhcFflTZ7 github.com/btcsuite/btcd v0.23.5-0.20231215221805-96c9fd8078fd/go.mod h1:nm3Bko6zh6bWP60UxwoT5LzdGJsQJaPo6HjduXq9p6A= github.com/btcsuite/btcd/btcec/v2 v2.1.0/go.mod h1:2VzYrv4Gm4apmbVVsSq5bqf1Ec8v56E48Vt0Y/umPgA= github.com/btcsuite/btcd/btcec/v2 v2.1.3/go.mod h1:ctjw4H1kknNJmRN4iP1R7bTQ+v3GJkZBd6mui8ZsAZE= -github.com/btcsuite/btcd/btcec/v2 v2.3.3 h1:6+iXlDKE8RMtKsvK0gshlXIuPbyWM/h84Ensb7o3sC0= -github.com/btcsuite/btcd/btcec/v2 v2.3.3/go.mod h1:zYzJ8etWJQIv1Ogk7OzpWjowwOdXY1W/17j2MW85J04= +github.com/btcsuite/btcd/btcec/v2 v2.3.4 h1:3EJjcN70HCu/mwqlUsGK8GcNVyLVxFDlWurTXGPFfiQ= +github.com/btcsuite/btcd/btcec/v2 v2.3.4/go.mod h1:zYzJ8etWJQIv1Ogk7OzpWjowwOdXY1W/17j2MW85J04= github.com/btcsuite/btcd/btcutil v1.0.0/go.mod h1:Uoxwv0pqYWhD//tfTiipkxNfdhG9UrLwaeswfjfdF0A= github.com/btcsuite/btcd/btcutil v1.1.0/go.mod h1:5OapHB7A2hBBWLm48mmw4MOHNJCcUBTwmWH/0Jn8VHE= github.com/btcsuite/btcd/btcutil v1.1.5 h1:+wER79R5670vs/ZusMTF1yTcRYE5GUsFbdjdisflzM8= @@ -89,8 +89,8 @@ github.com/gorilla/securecookie v1.1.1/go.mod h1:ra0sb63/xPlUeL+yeDciTfxMRAA+MP+ github.com/gorilla/sessions v1.2.1 h1:DHd3rPN5lE3Ts3D8rKkQ8x/0kqfeNmBAaiSi+o7FsgI= github.com/gorilla/sessions v1.2.1/go.mod h1:dk2InVEVJ0sfLlnXv9EAgkf6ecYs/i80K/zI+bUmuGM= github.com/gorilla/websocket v1.5.0/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= -github.com/gorilla/websocket v1.5.1 h1:gmztn0JnHVt9JZquRuzLw3g4wouNVzKL15iLr/zn/QY= -github.com/gorilla/websocket v1.5.1/go.mod h1:x3kM2JMyaluk02fnUJpQuwD2dCS5NDG2ZHL0uE0tcaY= +github.com/gorilla/websocket v1.5.3 h1:saDtZ6Pbx/0u+bgYQ3q96pZgCzfhKXGPqt7kZ72aNNg= +github.com/gorilla/websocket v1.5.3/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= github.com/gotuna/gotuna v0.6.0 h1:N1lQKXEi/lwRp8u3sccTYLhzOffA4QasExz/1M5Riws= github.com/gotuna/gotuna v0.6.0/go.mod h1:F/ecRt29ChB6Ycy1AFIBpBiMNK0j7Heq+gFbLWquhjc= github.com/grpc-ecosystem/grpc-gateway/v2 v2.20.0 h1:bkypFPDjIYGfCYD5mRBvpqxfYX1YCS1PXdKYWi8FsN0= @@ -110,8 +110,9 @@ github.com/libp2p/go-buffer-pool v0.1.0 h1:oK4mSFcQz7cTQIfqbe4MIj9gLW+mnanjyFtc6 github.com/libp2p/go-buffer-pool v0.1.0/go.mod h1:N+vh8gMqimBzdKkSMVuydVDq+UV5QTWy5HSiZacSbPg= github.com/lucasb-eyer/go-colorful v1.2.0 h1:1nnpGOrhyZZuNyfu1QjKiUICQ74+3FNCN69Aj6K7nkY= github.com/lucasb-eyer/go-colorful v1.2.0/go.mod h1:R4dSotOR9KMtayYi1e77YzuveK+i7ruzyGqttikkLy0= -github.com/mattn/go-runewidth v0.0.15 h1:UNAjwbU9l54TA3KzvqLGxwWjHmMgBUVhBiTjelZgg3U= github.com/mattn/go-runewidth v0.0.15/go.mod h1:Jdepj2loyihRzMpdS35Xk/zdY8IAYHsh153qUoGf23w= +github.com/mattn/go-runewidth v0.0.16 h1:E5ScNMtiwvlvB5paMFdw9p4kSQzbXFikJ5SQO6TULQc= +github.com/mattn/go-runewidth v0.0.16/go.mod h1:Jdepj2loyihRzMpdS35Xk/zdY8IAYHsh153qUoGf23w= github.com/nxadm/tail v1.4.4/go.mod h1:kenIhsEOeOJmVchQTgglprH7qJGnHDVpk1VPCcaMI8A= github.com/nxadm/tail v1.4.11 h1:8feyoE3OzPrcshW5/MJ4sGESc5cqmGkGCWlco4l0bqY= github.com/nxadm/tail v1.4.11/go.mod h1:OTaG3NK980DZzxbRq6lEuzgU+mug70nY11sMd4JXXHc= @@ -153,8 +154,8 @@ github.com/zondax/hid v0.9.2 h1:WCJFnEDMiqGF64nlZz28E9qLVZ0KSJ7xpc5DLEyma2U= github.com/zondax/hid v0.9.2/go.mod h1:l5wttcP0jwtdLjqjMMWFVEE7d1zO0jvSPA9OPZxWpEM= github.com/zondax/ledger-go v0.14.3 h1:wEpJt2CEcBJ428md/5MgSLsXLBos98sBOyxNmCjfUCw= github.com/zondax/ledger-go v0.14.3/go.mod h1:IKKaoxupuB43g4NxeQmbLXv7T9AlQyie1UpHb342ycI= -go.etcd.io/bbolt v1.3.9 h1:8x7aARPEXiXbHmtUwAIv7eV2fQFHrLLavdiJ3uzJXoI= -go.etcd.io/bbolt v1.3.9/go.mod h1:zaO32+Ti0PK1ivdPtgMESzuzL2VPoIG1PCQNvOdo/dE= +go.etcd.io/bbolt v1.3.10 h1:+BqfJTcCzTItrop8mq/lbzL8wSGtj94UO/3U31shqG0= +go.etcd.io/bbolt v1.3.10/go.mod h1:bK3UQLPJZly7IlNmV7uVHJDxfe5aK9Ll93e/74Y9oEQ= go.opentelemetry.io/otel v1.28.0 h1:/SqNcYk+idO0CxKEUOtKQClMK/MimZihKYMruSMViUo= go.opentelemetry.io/otel v1.28.0/go.mod h1:q68ijF8Fc8CnMHKyzqL6akLO46ePnjkgfIMIjUIX9z4= go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetricgrpc v1.28.0 h1:U2guen0GhqH8o/G2un8f/aG/y++OuW6MyCo6hT9prXk= @@ -244,8 +245,8 @@ golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGm golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc= golang.org/x/tools v0.6.0/go.mod h1:Xwgl3UAJ/d3gWutnCtw505GrjyAbvKui8lOU390QaIU= -golang.org/x/tools v0.22.0 h1:gqSGLZqv+AI9lIQzniJ0nZDRG5GBPsSi+DRNHWNz6yA= -golang.org/x/tools v0.22.0/go.mod h1:aCwcsjqvq7Yqt6TNyX7QMU2enbQ/Gt0bo6krSeEri+c= +golang.org/x/tools v0.23.0 h1:SGsXPZ+2l4JsgaCKkx+FQ9YZ5XEtA1GZYuoDjenLjvg= +golang.org/x/tools v0.23.0/go.mod h1:pnu6ufv6vQkll6szChhK3C3L/ruaIv5eBeztNG8wtsI= golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE= From 5f2880359591e54d63ec2a3c35fcc1fb37c8988e Mon Sep 17 00:00:00 2001 From: Morgan Date: Wed, 31 Jul 2024 03:48:12 +0200 Subject: [PATCH 5/7] ci: fix backwards incompatible change (#2644) https://github.com/gnolang/gno/pull/2612 for some reason only had two checks. Hopefully this has changed with the latest changes to CI. --- tm2/pkg/crypto/secp256k1/secp256k1_nocgo.go | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/tm2/pkg/crypto/secp256k1/secp256k1_nocgo.go b/tm2/pkg/crypto/secp256k1/secp256k1_nocgo.go index ccf2104a8d3..3e89515294d 100644 --- a/tm2/pkg/crypto/secp256k1/secp256k1_nocgo.go +++ b/tm2/pkg/crypto/secp256k1/secp256k1_nocgo.go @@ -15,10 +15,7 @@ import ( func (privKey PrivKeySecp256k1) Sign(msg []byte) ([]byte, error) { priv, _ := btcec.PrivKeyFromBytes(privKey[:]) - sig, err := ecdsa.SignCompact(priv, crypto.Sha256(msg), false) // ref uncompressed pubkey - if err != nil { - return nil, err - } + sig := ecdsa.SignCompact(priv, crypto.Sha256(msg), false) // ref uncompressed pubkey // remove compact sig recovery code byte at the beginning return sig[1:], nil From 14b9015875ee557008cb55b0bc454dcd326070d1 Mon Sep 17 00:00:00 2001 From: deelawn Date: Wed, 31 Jul 2024 22:02:18 +0100 Subject: [PATCH 6/7] fix(gnovm): fix max names in block check (#2645) I noticed this while reviewing #2429. The previous conditional could never evaluate to true: `if (1<<16 - 1) < sb.NumNames {`. `sb.NumNames` is a `uint16` and the value it is being compared to, `1<<16 - 1` is the max uint16 value, so it is impossible the the number of names to be greater than this value. Instead, we should check to see if the current number of names is the maximum value and panic if this is the case.
Contributors' checklist... - [x] Added new tests, or not needed, or not feasible - [x] Provided an example (e.g. screenshot) to aid review or the PR is self-explanatory - [x] Updated the official documentation or not needed - [x] No breaking changes were made, or a `BREAKING CHANGE: xxx` message was included in the description - [x] Added references to related issues and PRs - [x] Provided any useful hints for running manual tests - [x] Added new benchmarks to [generated graphs](https://gnoland.github.io/benchmarks), if any. More info [here](https://github.com/gnolang/gno/blob/master/.benchmarks/README.md).
--- gnovm/pkg/gnolang/nodes.go | 3 ++- gnovm/pkg/gnolang/nodes_test.go | 44 +++++++++++++++++++++++++++++++++ 2 files changed, 46 insertions(+), 1 deletion(-) create mode 100644 gnovm/pkg/gnolang/nodes_test.go diff --git a/gnovm/pkg/gnolang/nodes.go b/gnovm/pkg/gnolang/nodes.go index c578d2a3ec3..b18ed157ca6 100644 --- a/gnovm/pkg/gnolang/nodes.go +++ b/gnovm/pkg/gnolang/nodes.go @@ -4,6 +4,7 @@ import ( "fmt" "go/parser" "go/token" + "math" "os" "path/filepath" "reflect" @@ -1802,7 +1803,7 @@ func (sb *StaticBlock) Define2(isConst bool, n Name, st Type, tv TypedValue) { if int(sb.NumNames) != len(sb.Names) { panic("StaticBlock.NumNames and len(.Names) mismatch") } - if (1<<16 - 1) < sb.NumNames { + if sb.NumNames == math.MaxUint16 { panic("too many variables in block") } if tv.T == nil && tv.V != nil { diff --git a/gnovm/pkg/gnolang/nodes_test.go b/gnovm/pkg/gnolang/nodes_test.go new file mode 100644 index 00000000000..2c3a03d8c09 --- /dev/null +++ b/gnovm/pkg/gnolang/nodes_test.go @@ -0,0 +1,44 @@ +package gnolang_test + +import ( + "math" + "testing" + + "github.com/gnolang/gno/gnovm/pkg/gnolang" +) + +func TestStaticBlock_Define2_MaxNames(t *testing.T) { + defer func() { + if r := recover(); r != nil { + panicString, ok := r.(string) + if !ok { + t.Errorf("expected panic string, got %v", r) + } + + if panicString != "too many variables in block" { + t.Errorf("expected panic string to be 'too many variables in block', got '%s'", panicString) + } + + return + } + + // If it didn't panic, fail. + t.Errorf("expected panic when exceeding maximum number of names") + }() + + staticBlock := new(gnolang.StaticBlock) + staticBlock.NumNames = math.MaxUint16 - 1 + staticBlock.Names = make([]gnolang.Name, staticBlock.NumNames) + + // Adding one more is okay. + staticBlock.Define2(false, gnolang.Name("a"), gnolang.BoolType, gnolang.TypedValue{T: gnolang.BoolType}) + if staticBlock.NumNames != math.MaxUint16 { + t.Errorf("expected NumNames to be %d, got %d", math.MaxUint16, staticBlock.NumNames) + } + if len(staticBlock.Names) != math.MaxUint16 { + t.Errorf("expected len(Names) to be %d, got %d", math.MaxUint16, len(staticBlock.Names)) + } + + // This one should panic because the maximum number of names has been reached. + staticBlock.Define2(false, gnolang.Name("a"), gnolang.BoolType, gnolang.TypedValue{T: gnolang.BoolType}) +} From 56f83579ae78fc1b5718d719f255b18c9c66f0cc Mon Sep 17 00:00:00 2001 From: 6h057 <15034695+omarsy@users.noreply.github.com> Date: Fri, 2 Aug 2024 16:10:44 +0200 Subject: [PATCH 7/7] feat(gnovm): add stacktraces and log them in panic messages (#2145) Closes #1812 #### Summary This pull request introduces a new `StackTrace` mechanism to the `Machine.Exceptions` class, enhancing its exception handling capabilities by generating and appending detailed stacktraces during panic situations. **Panic Handling:** - When a panic occurs, the current stack state is copied and appended to the exception details. - This includes the value of the panic, the last call frame, and the copied stack trace. **Code Example:** ```go package main func main() { f() } func f() { defer func() { panic("third") }() defer func() { panic("second") }() panic("first") } ``` **Sample Output:** ``` Stacktrace: Exception 0: panic((const ("first" string))) main/files/panic0b.gno:14 f() main/files/panic0b.gno:4 Exception 1: panic((const ("second" string))) main/files/panic0b.gno:12 f() main/files/panic0b.gno:4 Exception 2: panic((const ("third" string))) main/files/panic0b.gno:9 f() main/files/panic0b.gno:4 ```
Contributors' checklist... - [ ] Added new tests, or not needed, or not feasible - [ ] Provided an example (e.g. screenshot) to aid review or the PR is self-explanatory - [ ] Updated the official documentation or not needed - [ ] No breaking changes were made, or a `BREAKING CHANGE: xxx` message was included in the description - [ ] Added references to related issues and PRs - [ ] Provided any useful hints for running manual tests - [ ] Added new benchmarks to [generated graphs](https://gnoland.github.io/benchmarks), if any. More info [here](https://github.com/gnolang/gno/blob/master/.benchmarks/README.md).
--------- Co-authored-by: Morgan --- gno.land/cmd/gnoland/testdata/panic.txtar | 27 +++ gno.land/pkg/sdk/vm/keeper.go | 9 +- gnovm/cmd/gno/run.go | 10 +- gnovm/pkg/gnolang/debugger_test.go | 20 +- gnovm/pkg/gnolang/eval_test.go | 66 ++++-- gnovm/pkg/gnolang/frame.go | 123 ++++++++++ gnovm/pkg/gnolang/machine.go | 115 +++++++-- gnovm/pkg/gnolang/op_call.go | 4 +- gnovm/tests/file.go | 56 ++++- gnovm/tests/files/panic0.gno | 5 + gnovm/tests/files/panic0a.gno | 45 ++++ gnovm/tests/files/panic0b.gno | 13 + gnovm/tests/files/panic0c.gno | 87 +++++++ gnovm/tests/files/panic1.gno | 5 + gnovm/tests/files/panic2a.gno | 275 ++++++++++++++++++++++ gnovm/tests/files/panic2b.gno | 44 ++++ gnovm/tests/files/recover10.gno | 5 + gnovm/tests/files/recover1b.gno | 5 + gnovm/tests/files/recover8.gno | 7 + gnovm/tests/files/std5_stdlibs.gno | 9 + gnovm/tests/files/std8_stdlibs.gno | 13 + gnovm/tests/files/time17_native.gno | 20 ++ gnovm/tests/files/typeassert1.gno | 5 + gnovm/tests/files/typeassert2a.gno | 5 + gnovm/tests/files/typeassert9.gno | 5 + gnovm/tests/files/zrealm_panic.gno | 20 ++ 26 files changed, 947 insertions(+), 51 deletions(-) create mode 100644 gno.land/cmd/gnoland/testdata/panic.txtar create mode 100644 gnovm/tests/files/panic0a.gno create mode 100644 gnovm/tests/files/panic0c.gno create mode 100644 gnovm/tests/files/panic2a.gno create mode 100644 gnovm/tests/files/panic2b.gno create mode 100644 gnovm/tests/files/time17_native.gno create mode 100644 gnovm/tests/files/zrealm_panic.gno diff --git a/gno.land/cmd/gnoland/testdata/panic.txtar b/gno.land/cmd/gnoland/testdata/panic.txtar new file mode 100644 index 00000000000..2b964d80751 --- /dev/null +++ b/gno.land/cmd/gnoland/testdata/panic.txtar @@ -0,0 +1,27 @@ +# test panic + +loadpkg gno.land/r/demo/panic $WORK + +# start a new node +gnoland start + + +! gnokey maketx call -pkgpath gno.land/r/demo/panic --func Trigger --gas-fee 1000000ugnot --gas-wanted 2000000 --broadcast -chainid=tendermint_test test1 + +stderr 'p\\(\)' +stderr 'gno.land/r/demo/panic/panic.gno:5' +stderr 'pkg\\.Trigger\(\)' +stderr 'gno.land/r/demo/panic/panic.gno:9' + +-- panic.gno -- +package main + +func p() { + i := "here" + panic(i) +} + +func Trigger() { + p() +} + diff --git a/gno.land/pkg/sdk/vm/keeper.go b/gno.land/pkg/sdk/vm/keeper.go index 934c4557dd0..615be2029fe 100644 --- a/gno.land/pkg/sdk/vm/keeper.go +++ b/gno.land/pkg/sdk/vm/keeper.go @@ -537,12 +537,15 @@ func (vm *VMKeeper) Call(ctx sdk.Context, msg MsgCall) (res string, err error) { m.SetActivePackage(mpv) defer func() { if r := recover(); r != nil { - switch r.(type) { + switch r := r.(type) { case store.OutOfGasException: // panic in consumeGas() panic(r) + case gno.UnhandledPanicError: + err = errors.Wrap(fmt.Errorf("%v", r.Error()), "VM call panic: %s\nStacktrace: %s\n", + r.Error(), m.ExceptionsStacktrace()) default: - err = errors.Wrap(fmt.Errorf("%v", r), "VM call panic: %v\n%s\n", - r, m.String()) + err = errors.Wrap(fmt.Errorf("%v", r), "VM call panic: %v\nMachine State:%s\nStacktrace: %s\n", + r, m.String(), m.Stacktrace().String()) return } } diff --git a/gnovm/cmd/gno/run.go b/gnovm/cmd/gno/run.go index 39306d59cb0..cfbfe995a46 100644 --- a/gnovm/cmd/gno/run.go +++ b/gnovm/cmd/gno/run.go @@ -188,8 +188,14 @@ func listNonTestFiles(dir string) ([]string, error) { func runExpr(m *gno.Machine, expr string) { defer func() { if r := recover(); r != nil { - fmt.Printf("panic running expression %s: %v\n%s\n", - expr, r, m.String()) + switch r := r.(type) { + case gno.UnhandledPanicError: + fmt.Printf("panic running expression %s: %v\nStacktrace: %s\n", + expr, r.Error(), m.ExceptionsStacktrace()) + default: + fmt.Printf("panic running expression %s: %v\nMachine State:%s\nStacktrace: %s\n", + expr, r, m.String(), m.Stacktrace().String()) + } panic(r) } }() diff --git a/gnovm/pkg/gnolang/debugger_test.go b/gnovm/pkg/gnolang/debugger_test.go index 10d7c5ce250..16ecb91fb3c 100644 --- a/gnovm/pkg/gnolang/debugger_test.go +++ b/gnovm/pkg/gnolang/debugger_test.go @@ -24,7 +24,7 @@ type writeNopCloser struct{ io.Writer } func (writeNopCloser) Close() error { return nil } // TODO (Marc): move evalTest to gnovm/tests package and remove code duplicates -func evalTest(debugAddr, in, file string) (out, err string) { +func evalTest(debugAddr, in, file string) (out, err, stacktrace string) { bout := bytes.NewBufferString("") berr := bytes.NewBufferString("") stdin := bytes.NewBufferString(in) @@ -58,6 +58,18 @@ func evalTest(debugAddr, in, file string) (out, err string) { }) defer m.Release() + defer func() { + if r := recover(); r != nil { + switch r.(type) { + case gnolang.UnhandledPanicError: + stacktrace = m.ExceptionsStacktrace() + default: + stacktrace = m.Stacktrace().String() + } + stacktrace = strings.TrimSpace(strings.ReplaceAll(stacktrace, "../../tests/files/", "files/")) + panic(r) + } + }() if debugAddr != "" { if e := m.Debugger.Serve(debugAddr); e != nil { @@ -69,7 +81,7 @@ func evalTest(debugAddr, in, file string) (out, err string) { m.RunFiles(f) ex, _ := gnolang.ParseExpr("main()") m.Eval(ex) - out, err = bout.String(), berr.String() + out, err, stacktrace = bout.String(), berr.String(), m.ExceptionsStacktrace() return } @@ -78,7 +90,7 @@ func runDebugTest(t *testing.T, targetPath string, tests []dtest) { for _, test := range tests { t.Run("", func(t *testing.T) { - out, err := evalTest("", test.in, targetPath) + out, err, _ := evalTest("", test.in, targetPath) t.Log("in:", test.in, "out:", out, "err:", err) if !strings.Contains(out, test.out) { t.Errorf("unexpected output\nwant\"%s\"\n got \"%s\"", test.out, out) @@ -194,7 +206,7 @@ func TestRemoteDebug(t *testing.T) { } func TestRemoteError(t *testing.T) { - _, err := evalTest(":xxx", "", debugTarget) + _, err, _ := evalTest(":xxx", "", debugTarget) t.Log("err:", err) if !strings.Contains(err, "tcp/xxx: unknown port") && !strings.Contains(err, "tcp/xxx: nodename nor servname provided, or not known") { diff --git a/gnovm/pkg/gnolang/eval_test.go b/gnovm/pkg/gnolang/eval_test.go index fdd8e0204d1..5aa5bcca462 100644 --- a/gnovm/pkg/gnolang/eval_test.go +++ b/gnovm/pkg/gnolang/eval_test.go @@ -3,6 +3,7 @@ package gnolang_test import ( "os" "path" + "sort" "strings" "testing" ) @@ -14,17 +15,21 @@ func TestEvalFiles(t *testing.T) { t.Fatal(err) } for _, f := range files { - wantOut, wantErr, ok := testData(dir, f) + wantOut, wantErr, wantStacktrace, ok := testData(dir, f) if !ok { continue } t.Run(f.Name(), func(t *testing.T) { - out, err := evalTest("", "", path.Join(dir, f.Name())) + out, err, stacktrace := evalTest("", "", path.Join(dir, f.Name())) if wantErr != "" && !strings.Contains(err, wantErr) || wantErr == "" && err != "" { t.Fatalf("unexpected error\nWant: %s\n Got: %s", wantErr, err) } + + if wantStacktrace != "" && !strings.Contains(stacktrace, wantStacktrace) { + t.Fatalf("unexpected stacktrace\nWant: %s\n Got: %s", wantStacktrace, stacktrace) + } if wantOut != "" && out != wantOut { t.Fatalf("unexpected output\nWant: %s\n Got: %s", wantOut, out) } @@ -33,30 +38,63 @@ func TestEvalFiles(t *testing.T) { } // testData returns the expected output and error string, and true if entry is valid. -func testData(dir string, f os.DirEntry) (testOut, testErr string, ok bool) { +func testData(dir string, f os.DirEntry) (testOut, testErr, testStacktrace string, ok bool) { if f.IsDir() { - return "", "", false + return } name := path.Join(dir, f.Name()) if !strings.HasSuffix(name, ".gno") || strings.HasSuffix(name, "_long.gno") { - return "", "", false + return } buf, err := os.ReadFile(name) if err != nil { - return "", "", false + return } str := string(buf) if strings.Contains(str, "// PKGPATH:") { - return "", "", false + return } - return commentFrom(str, "\n// Output:"), commentFrom(str, "\n// Error:"), true + + res := commentFrom(str, []string{"\n// Output:", "\n// Error:", "\n// Stacktrace:"}) + + return res[0], res[1], res[2], true } -// commentFrom returns the content from a trailing comment block in s starting with delim. -func commentFrom(s, delim string) string { - index := strings.Index(s, delim) - if index < 0 { - return "" +type directive struct { + delim string + res string + index int +} + +// commentFrom returns the comments from s that are between the delimiters. +func commentFrom(s string, delims []string) []string { + directives := make([]directive, len(delims)) + directivesFound := make([]*directive, 0, len(delims)) + + for i, delim := range delims { + index := strings.Index(s, delim) + directives[i] = directive{delim: delim, index: index} + if index >= 0 { + directivesFound = append(directivesFound, &directives[i]) + } } - return strings.TrimSpace(strings.ReplaceAll(s[index+len(delim):], "\n// ", "\n")) + sort.Slice(directivesFound, func(i, j int) bool { + return directivesFound[i].index < directivesFound[j].index + }) + + for i := range directivesFound { + next := len(s) + if i != len(directivesFound)-1 { + next = directivesFound[i+1].index + } + + directivesFound[i].res = strings.TrimSpace(strings.ReplaceAll(s[directivesFound[i].index+len(directivesFound[i].delim):next], "\n// ", "\n")) + } + + res := make([]string, len(directives)) + for i, d := range directives { + res[i] = d.res + } + + return res } diff --git a/gnovm/pkg/gnolang/frame.go b/gnovm/pkg/gnolang/frame.go index c808fc111b0..2ac1027eb32 100644 --- a/gnovm/pkg/gnolang/frame.go +++ b/gnovm/pkg/gnolang/frame.go @@ -2,8 +2,11 @@ package gnolang import ( "fmt" + "strings" ) +const maxStacktraceSize = 128 + //---------------------------------------- // (runtime) Frame @@ -64,6 +67,10 @@ func (fr Frame) String() string { } } +func (fr *Frame) IsCall() bool { + return fr.Func != nil || fr.GoFunc != nil +} + func (fr *Frame) PushDefer(dfr Defer) { fr.Defers = append(fr.Defers, dfr) } @@ -92,3 +99,119 @@ type Defer struct { // a panic occurs and is decremented each time a panic is recovered. PanicScope uint } + +type StacktraceCall struct { + Stmt Stmt + Frame *Frame +} +type Stacktrace struct { + Calls []StacktraceCall + NumFramesElided int +} + +func (s Stacktrace) String() string { + var builder strings.Builder + + for i := 0; i < len(s.Calls); i++ { + if s.NumFramesElided > 0 && i == maxStacktraceSize/2 { + fmt.Fprintf(&builder, "...%d frame(s) elided...\n", s.NumFramesElided) + } + + call := s.Calls[i] + cx := call.Frame.Source.(*CallExpr) + switch { + case call.Frame.Func != nil && call.Frame.Func.IsNative(): + fmt.Fprintf(&builder, "%s\n", toExprTrace(cx)) + fmt.Fprintf(&builder, " gonative:%s.%s\n", call.Frame.Func.NativePkg, call.Frame.Func.NativeName) + case call.Frame.Func != nil: + fmt.Fprintf(&builder, "%s\n", toExprTrace(cx)) + fmt.Fprintf(&builder, " %s/%s:%d\n", call.Frame.Func.PkgPath, call.Frame.Func.FileName, call.Stmt.GetLine()) + case call.Frame.GoFunc != nil: + fmt.Fprintf(&builder, "%s\n", toExprTrace(cx)) + fmt.Fprintf(&builder, " gofunction:%s\n", call.Frame.GoFunc.Value.Type()) + default: + panic("StacktraceCall has a non-call Frame") + } + } + return builder.String() +} + +func toExprTrace(ex Expr) string { + switch ex := ex.(type) { + case *CallExpr: + s := make([]string, len(ex.Args)) + for i, arg := range ex.Args { + s[i] = toExprTrace(arg) + } + return fmt.Sprintf("%s(%s)", toExprTrace(ex.Func), strings.Join(s, ",")) + case *BinaryExpr: + return fmt.Sprintf("%s %s %s", toExprTrace(ex.Left), ex.Op.TokenString(), toExprTrace(ex.Right)) + case *UnaryExpr: + return fmt.Sprintf("%s%s", ex.Op.TokenString(), toExprTrace(ex.X)) + case *SelectorExpr: + return fmt.Sprintf("%s.%s", toExprTrace(ex.X), ex.Sel) + case *IndexExpr: + return fmt.Sprintf("%s[%s]", toExprTrace(ex.X), toExprTrace(ex.Index)) + case *StarExpr: + return fmt.Sprintf("*%s", toExprTrace(ex.X)) + case *RefExpr: + return fmt.Sprintf("&%s", toExprTrace(ex.X)) + case *CompositeLitExpr: + lenEl := len(ex.Elts) + if ex.Type == nil { + return fmt.Sprintf("", lenEl) + } + + return fmt.Sprintf("%s", toExprTrace(ex.Type), lenEl) + case *FuncLitExpr: + return fmt.Sprintf("%s{ ... }", toExprTrace(&ex.Type)) + case *TypeAssertExpr: + return fmt.Sprintf("%s.(%s)", toExprTrace(ex.X), toExprTrace(ex.Type)) + case *ConstExpr: + return toConstExpTrace(ex) + case *NameExpr, *BasicLitExpr, *SliceExpr: + return ex.String() + } + + return ex.String() +} + +func toConstExpTrace(cte *ConstExpr) string { + tv := cte.TypedValue + + switch bt := baseOf(tv.T).(type) { + case PrimitiveType: + switch bt { + case UntypedBoolType, BoolType: + return fmt.Sprintf("%t", tv.GetBool()) + case UntypedStringType, StringType: + return tv.GetString() + case IntType: + return fmt.Sprintf("%d", tv.GetInt()) + case Int8Type: + return fmt.Sprintf("%d", tv.GetInt8()) + case Int16Type: + return fmt.Sprintf("%d", tv.GetInt16()) + case UntypedRuneType, Int32Type: + return fmt.Sprintf("%d", tv.GetInt32()) + case Int64Type: + return fmt.Sprintf("%d", tv.GetInt64()) + case UintType: + return fmt.Sprintf("%d", tv.GetUint()) + case Uint8Type: + return fmt.Sprintf("%d", tv.GetUint8()) + case Uint16Type: + return fmt.Sprintf("%d", tv.GetUint16()) + case Uint32Type: + return fmt.Sprintf("%d", tv.GetUint32()) + case Uint64Type: + return fmt.Sprintf("%d", tv.GetUint64()) + case Float32Type: + return fmt.Sprintf("%v", tv.GetFloat32()) + case Float64Type: + return fmt.Sprintf("%v", tv.GetFloat64()) + } + } + + return tv.T.String() +} diff --git a/gnovm/pkg/gnolang/machine.go b/gnovm/pkg/gnolang/machine.go index 850da3d3c0f..24f94abc10b 100644 --- a/gnovm/pkg/gnolang/machine.go +++ b/gnovm/pkg/gnolang/machine.go @@ -25,12 +25,23 @@ type Exception struct { // Frame is used to reference the frame a panic occurred in so that recover() knows if the // currently executing deferred function is able to recover from the panic. Frame *Frame + + Stacktrace Stacktrace } func (e Exception) Sprint(m *Machine) string { return e.Value.Sprint(m) } +// UnhandledPanicError represents an error thrown when a panic is not handled in the realm. +type UnhandledPanicError struct { + Descriptor string // Description of the unhandled panic. +} + +func (e UnhandledPanicError) Error() string { + return e.Descriptor +} + //---------------------------------------- // Machine @@ -457,6 +468,43 @@ func (m *Machine) TestFunc(t *testing.T, tv TypedValue) { }) } +// Stacktrace returns the stack trace of the machine. +// It collects the executions and frames from the machine's frames and statements. +func (m *Machine) Stacktrace() (stacktrace Stacktrace) { + if len(m.Frames) == 0 { + return + } + + calls := make([]StacktraceCall, 0, len(m.Stmts)) + nextStmtIndex := len(m.Stmts) - 1 + for i := len(m.Frames) - 1; i >= 0; i-- { + if m.Frames[i].IsCall() { + stm := m.Stmts[nextStmtIndex] + bs := stm.(*bodyStmt) + stm = bs.Body[bs.NextBodyIndex-1] + calls = append(calls, StacktraceCall{ + Stmt: stm, + Frame: m.Frames[i], + }) + } + // if the frame is a call, the next statement is the last statement of the frame. + nextStmtIndex = m.Frames[i].NumStmts - 1 + } + + // if the stacktrace is too long, we trim it down to maxStacktraceSize + if len(calls) > maxStacktraceSize { + const halfMax = maxStacktraceSize / 2 + + stacktrace.NumFramesElided = len(calls) - maxStacktraceSize + calls = append(calls[:halfMax], calls[len(calls)-halfMax:]...) + calls = calls[:len(calls):len(calls)] // makes remaining part of "calls" GC'able + } + + stacktrace.Calls = calls + + return +} + // in case of panic, inject location information to exception. func (m *Machine) injectLocOnPanic() { if r := recover(); r != nil { @@ -736,8 +784,14 @@ func (m *Machine) resavePackageValues(rlm *Realm) { func (m *Machine) RunFunc(fn Name) { defer func() { if r := recover(); r != nil { - fmt.Printf("Machine.RunFunc(%q) panic: %v\n%s\n", - fn, r, m.String()) + switch r := r.(type) { + case UnhandledPanicError: + fmt.Printf("Machine.RunFunc(%q) panic: %s\nStacktrace: %s\n", + fn, r.Error(), m.ExceptionsStacktrace()) + default: + fmt.Printf("Machine.RunFunc(%q) panic: %v\nMachine State:%s\nStacktrace: %s\n", + fn, r, m.String(), m.Stacktrace().String()) + } panic(r) } }() @@ -747,8 +801,14 @@ func (m *Machine) RunFunc(fn Name) { func (m *Machine) RunMain() { defer func() { if r := recover(); r != nil { - fmt.Printf("Machine.RunMain() panic: %v\n%s\n", - r, m.String()) + switch r := r.(type) { + case UnhandledPanicError: + fmt.Printf("Machine.RunMain() panic: %s\nStacktrace: %s\n", + r.Error(), m.ExceptionsStacktrace()) + default: + fmt.Printf("Machine.RunMain() panic: %v\nMachine State:%s\nStacktrace: %s\n", + r, m.String(), m.Stacktrace()) + } panic(r) } }() @@ -1606,11 +1666,11 @@ func (m *Machine) PopStmt() Stmt { } if bs, ok := s.(*bodyStmt); ok { return bs.PopActiveStmt() - } else { - // general case. - m.Stmts = m.Stmts[:numStmts-1] - return s } + + m.Stmts = m.Stmts[:numStmts-1] + + return s } func (m *Machine) ForcePopStmt() (s Stmt) { @@ -1855,6 +1915,7 @@ func (m *Machine) PopFrame() Frame { m.Printf("-F %#v\n", f) } m.Frames = m.Frames[:numFrames-1] + return *f } @@ -1874,8 +1935,7 @@ func (m *Machine) PopFrameAndReturn() { fr := m.PopFrame() fr.Popped = true if debug { - // TODO: optimize with fr.IsCall - if fr.Func == nil && fr.GoFunc == nil { + if !fr.IsCall() { panic("unexpected non-call (loop) frame") } } @@ -1951,8 +2011,7 @@ func (m *Machine) lastCallFrame(n int, mustBeFound bool) *Frame { } for i := len(m.Frames) - 1; i >= 0; i-- { fr := m.Frames[i] - if fr.Func != nil || fr.GoFunc != nil { - // TODO: optimize with fr.IsCall + if fr.IsCall() { if n == 1 { return fr } else { @@ -1973,8 +2032,7 @@ func (m *Machine) lastCallFrame(n int, mustBeFound bool) *Frame { func (m *Machine) PopUntilLastCallFrame() *Frame { for i := len(m.Frames) - 1; i >= 0; i-- { fr := m.Frames[i] - if fr.Func != nil || fr.GoFunc != nil { - // TODO: optimize with fr.IsCall + if fr.IsCall() { m.Frames = m.Frames[:i+1] return fr } @@ -2085,8 +2143,9 @@ func (m *Machine) Panic(ex TypedValue) { m.Exceptions = append( m.Exceptions, Exception{ - Value: ex, - Frame: m.MustLastCallFrame(1), + Value: ex, + Frame: m.MustLastCallFrame(1), + Stacktrace: m.Stacktrace(), }, ) @@ -2231,6 +2290,30 @@ func (m *Machine) String() string { return builder.String() } +func (m *Machine) ExceptionsStacktrace() string { + if len(m.Exceptions) == 0 { + return "" + } + + var builder strings.Builder + + ex := m.Exceptions[0] + builder.WriteString("panic: " + ex.Sprint(m) + "\n") + builder.WriteString(ex.Stacktrace.String()) + + switch { + case len(m.Exceptions) > 2: + fmt.Fprintf(&builder, "... %d panic(s) elided ...\n", len(m.Exceptions)-2) + fallthrough // to print last exception + case len(m.Exceptions) == 2: + ex = m.Exceptions[len(m.Exceptions)-1] + builder.WriteString("panic: " + ex.Sprint(m) + "\n") + builder.WriteString(ex.Stacktrace.String()) + } + + return builder.String() +} + //---------------------------------------- // utility diff --git a/gnovm/pkg/gnolang/op_call.go b/gnovm/pkg/gnolang/op_call.go index 5479ee6d5ae..15531ec610d 100644 --- a/gnovm/pkg/gnolang/op_call.go +++ b/gnovm/pkg/gnolang/op_call.go @@ -427,7 +427,9 @@ func (m *Machine) doOpPanic2() { for i, ex := range m.Exceptions { exs[i] = ex.Sprint(m) } - panic(strings.Join(exs, "\n\t")) + panic(UnhandledPanicError{ + Descriptor: strings.Join(exs, "\n\t"), + }) } m.PushOp(OpPanic2) m.PushOp(OpReturnCallDefers) // XXX rename, not return? diff --git a/gnovm/tests/file.go b/gnovm/tests/file.go index 8ab60145bd5..3fea714b142 100644 --- a/gnovm/tests/file.go +++ b/gnovm/tests/file.go @@ -109,7 +109,7 @@ func RunFileTest(rootDir string, path string, opts ...RunFileTestOption) error { opt(&f) } - directives, pkgPath, resWanted, errWanted, rops, maxAlloc, send := wantedFromComment(path) + directives, pkgPath, resWanted, errWanted, rops, stacktraceWanted, maxAlloc, send := wantedFromComment(path) if pkgPath == "" { pkgPath = "main" } @@ -124,6 +124,7 @@ func RunFileTest(rootDir string, path string, opts ...RunFileTestOption) error { store := TestStore(rootDir, "./files", stdin, stdout, stderr, mode) store.SetLogStoreOps(true) m := testMachineCustom(store, pkgPath, stdout, maxAlloc, send) + checkMachineIsEmpty := true // TODO support stdlib groups, but make testing safe; // e.g. not be able to make network connections. @@ -259,6 +260,8 @@ func RunFileTest(rootDir string, path string, opts ...RunFileTestOption) error { errstr = v.Sprint(m) case *gno.PreprocessError: errstr = v.Unwrap().Error() + case gno.UnhandledPanicError: + errstr = v.Error() default: errstr = strings.TrimSpace(fmt.Sprintf("%v", pnc)) } @@ -279,7 +282,7 @@ func RunFileTest(rootDir string, path string, opts ...RunFileTestOption) error { // NOTE: ignores any gno.GetDebugErrors(). gno.ClearDebugErrors() - return nil // nothing more to do. + checkMachineIsEmpty = false // nothing more to do. } else { // record errors when errWanted is empty and pnc not nil if pnc != nil { @@ -307,7 +310,7 @@ func RunFileTest(rootDir string, path string, opts ...RunFileTestOption) error { panic(fmt.Sprintf("fail on %s: got unexpected debug error(s): %v", path, gno.GetDebugErrors())) } // pnc is nil, errWanted empty, no gno debug errors - return nil + checkMachineIsEmpty = false } case "Output": // panic if got unexpected error @@ -373,24 +376,51 @@ func RunFileTest(rootDir string, path string, opts ...RunFileTestOption) error { } } } + case "Stacktrace": + if stacktraceWanted != "" { + var stacktrace string + + switch pnc.(type) { + case gno.UnhandledPanicError: + stacktrace = m.ExceptionsStacktrace() + default: + stacktrace = m.Stacktrace().String() + } + + if !strings.Contains(stacktrace, stacktraceWanted) { + diff, _ := difflib.GetUnifiedDiffString(difflib.UnifiedDiff{ + A: difflib.SplitLines(stacktraceWanted), + B: difflib.SplitLines(stacktrace), + FromFile: "Expected", + FromDate: "", + ToFile: "Actual", + ToDate: "", + Context: 1, + }) + panic(fmt.Sprintf("fail on %s: diff:\n%s\n", path, diff)) + } + } + checkMachineIsEmpty = false default: - return nil + checkMachineIsEmpty = false } } } - // Check that machine is empty. - err = m.CheckEmpty() - if err != nil { - if f.logger != nil { - f.logger("last state: \n", m.String()) + if checkMachineIsEmpty { + // Check that machine is empty. + err = m.CheckEmpty() + if err != nil { + if f.logger != nil { + f.logger("last state: \n", m.String()) + } + panic(fmt.Sprintf("fail on %s: machine not empty after main: %v", path, err)) } - panic(fmt.Sprintf("fail on %s: machine not empty after main: %v", path, err)) } return nil } -func wantedFromComment(p string) (directives []string, pkgPath, res, err, rops string, maxAlloc int64, send std.Coins) { +func wantedFromComment(p string) (directives []string, pkgPath, res, err, rops, stacktrace string, maxAlloc int64, send std.Coins) { fset := token.NewFileSet() f, err2 := parser.ParseFile(fset, p, nil, parser.ParseComments) if err2 != nil { @@ -432,6 +462,10 @@ func wantedFromComment(p string) (directives []string, pkgPath, res, err, rops s rops = strings.TrimPrefix(text, "Realm:\n") rops = strings.TrimSpace(rops) directives = append(directives, "Realm") + } else if strings.HasPrefix(text, "Stacktrace:\n") { + stacktrace = strings.TrimPrefix(text, "Stacktrace:\n") + stacktrace = strings.TrimSpace(stacktrace) + directives = append(directives, "Stacktrace") } else { // ignore unexpected. } diff --git a/gnovm/tests/files/panic0.gno b/gnovm/tests/files/panic0.gno index 66a38b42c46..06460ca9d07 100644 --- a/gnovm/tests/files/panic0.gno +++ b/gnovm/tests/files/panic0.gno @@ -4,5 +4,10 @@ func main() { panic("wtf") } +// Stacktrace: +// panic: wtf +// main() +// main/files/panic0.gno:4 + // Error: // wtf diff --git a/gnovm/tests/files/panic0a.gno b/gnovm/tests/files/panic0a.gno new file mode 100644 index 00000000000..575bb7cce91 --- /dev/null +++ b/gnovm/tests/files/panic0a.gno @@ -0,0 +1,45 @@ +// Test panic with function call with all kind of expressions +package main + +type S struct { + s string +} + +func f(it1 int, it2, it3 int, pit *int, b bool, strs []string, s S, m map[string]string, t func(s string) string) { + panic("wtf") +} + +func main() { + vit := 1 + lit := []int{1} + var ( + pit *int = &vit + v interface{} + ) + b := true + v = 1 + + f( + v.(int), + lit[0], + *pit, + &vit, + !b, + []string{"a", "b"}, + S{s: "c"}, + map[string]string{"d": "gg", "test": "test"}, + func(s string) string { + return s + }, + ) +} + +// Stacktrace: +// panic: wtf +// f(v.((const-type int)),lit[0],*pit,&vit,!b,[](const-type string),S,map[(const-type string)] (const-type string),func(s (const-type string)) (const-type string){ ... }) +// main/files/panic0a.gno:9 +// main() +// main/files/panic0a.gno:22 + +// Error: +// wtf diff --git a/gnovm/tests/files/panic0b.gno b/gnovm/tests/files/panic0b.gno index bf3b343f785..55a7b21015a 100644 --- a/gnovm/tests/files/panic0b.gno +++ b/gnovm/tests/files/panic0b.gno @@ -14,6 +14,19 @@ func f() { panic("first") } +// Stacktrace: +// panic: first +// f() +// main/files/panic0b.gno:14 +// main() +// main/files/panic0b.gno:4 +// ... 1 panic(s) elided ... +// panic: third +// f() +// main/files/panic0b.gno:9 +// main() +// main/files/panic0b.gno:4 + // Error: // first // second diff --git a/gnovm/tests/files/panic0c.gno b/gnovm/tests/files/panic0c.gno new file mode 100644 index 00000000000..c331ee3bd17 --- /dev/null +++ b/gnovm/tests/files/panic0c.gno @@ -0,0 +1,87 @@ +package main + +type S struct { + s string +} + +func f( + s string, + b bool, + by byte, + it int, + it8 int8, + it16 int16, + it32 int32, + it64 int64, + uit uint, + uit8 uint8, + uit16 uint16, + uit32 uint32, + uit64 uint64, + ft32 float32, + ft64 float64, + strs []string, + st S, + m map[string]string, + t func(s string) string, +) { + panic("wtf") +} + +func main() { + strs := []string{"a", "b"} + st := S{"c"} + m := map[string]string{"d": "gg", "test": "test"} + t := func(s string) string { + return s + } + + const s string = "a" + + const b bool = true + + const by byte = 0 + + const it int = 1 + const it8 int8 = 1 + const it16 int16 = 1 + const it32 int32 = 1 + const it64 int64 = 1 + const uit uint = 1 + const uit8 uint8 = 1 + const uit16 uint16 = 1 + const uit32 uint32 = 1 + const uit64 uint64 = 1 + const ft32 float32 = 1 + const ft64 float64 = 1 + f( + s, + b, + by, + it, + it8, + it16, + it32, + it64, + uit, + uit8, + uit16, + uit32, + uit64, + ft32, + ft64, + strs, + st, + m, + t) +} + +// Stacktrace: +// panic: wtf +// f(a,true,0,1,1,1,1,1,1,1,1,1,1,1,1,strs,st,m,t) +// main/files/panic0c.gno:28 +// main() +// main/files/panic0c.gno:57 + +// Error: +// wtf diff --git a/gnovm/tests/files/panic1.gno b/gnovm/tests/files/panic1.gno index 483d43e53d1..235ba4a0b34 100644 --- a/gnovm/tests/files/panic1.gno +++ b/gnovm/tests/files/panic1.gno @@ -22,5 +22,10 @@ func main() { panic("here") } +// Stacktrace: +// panic: here +// main() +// main/files/panic1.gno:22 + // Error: // here diff --git a/gnovm/tests/files/panic2a.gno b/gnovm/tests/files/panic2a.gno new file mode 100644 index 00000000000..7310d6cce71 --- /dev/null +++ b/gnovm/tests/files/panic2a.gno @@ -0,0 +1,275 @@ +package main + +func p(i int) { + if i == 200 { + panic("here") + } + p(i + 1) +} + +func main() { + p(0) +} + +// Stacktrace: +// panic: here +// p(i + 1) +// main/files/panic2a.gno:5 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// ...74 frame(s) elided... +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(i + 1) +// main/files/panic2a.gno:7 +// p(0) +// main/files/panic2a.gno:7 +// main() +// main/files/panic2a.gno:11 + +// Error: +// here diff --git a/gnovm/tests/files/panic2b.gno b/gnovm/tests/files/panic2b.gno new file mode 100644 index 00000000000..7c356409aad --- /dev/null +++ b/gnovm/tests/files/panic2b.gno @@ -0,0 +1,44 @@ +package main + +func p(i int) { + defer func() { + panic("here") + }() + if i == 4 { + panic("here") + } + p(i + 1) +} + +func main() { + p(0) +} + +// Stacktrace: +// panic: here +// p(i + 1) +// main/files/panic2b.gno:8 +// p(i + 1) +// main/files/panic2b.gno:10 +// p(i + 1) +// main/files/panic2b.gno:10 +// p(i + 1) +// main/files/panic2b.gno:10 +// p(0) +// main/files/panic2b.gno:10 +// main() +// main/files/panic2b.gno:14 +// ... 4 panic(s) elided ... +// panic: here +// p(0) +// main/files/panic2b.gno:5 +// main() +// main/files/panic2b.gno:14 + +// Error: +// here +// here +// here +// here +// here +// here diff --git a/gnovm/tests/files/recover10.gno b/gnovm/tests/files/recover10.gno index 16dff4d4fed..de083a322a4 100644 --- a/gnovm/tests/files/recover10.gno +++ b/gnovm/tests/files/recover10.gno @@ -6,5 +6,10 @@ func main() { panic("ahhhhh") } +// Stacktrace: +// panic: ahhhhh +// main() +// main/files/recover10.gno:6 + // Error: // ahhhhh diff --git a/gnovm/tests/files/recover1b.gno b/gnovm/tests/files/recover1b.gno index 9e3b9ba72b6..978b4988329 100644 --- a/gnovm/tests/files/recover1b.gno +++ b/gnovm/tests/files/recover1b.gno @@ -10,5 +10,10 @@ func main() { panic("test panic") } +// Stacktrace: +// panic: other panic +// main() +// main/files/recover1b.gno:8 + // Error: // other panic diff --git a/gnovm/tests/files/recover8.gno b/gnovm/tests/files/recover8.gno index 53b31f05468..d144a4f986f 100644 --- a/gnovm/tests/files/recover8.gno +++ b/gnovm/tests/files/recover8.gno @@ -20,5 +20,12 @@ func main() { doSomething() } +// Stacktrace: +// panic: do something panic +// doSomething() +// main/files/recover8.gno:7 +// main() +// main/files/recover8.gno:20 + // Error: // do something panic diff --git a/gnovm/tests/files/std5_stdlibs.gno b/gnovm/tests/files/std5_stdlibs.gno index d8de58518f1..4afa09da8d3 100644 --- a/gnovm/tests/files/std5_stdlibs.gno +++ b/gnovm/tests/files/std5_stdlibs.gno @@ -11,5 +11,14 @@ func main() { println(caller2) } +// Stacktrace: +// panic: frame not found +// callerAt(n) +// gonative:std.callerAt +// std.GetCallerAt(2) +// std/native.gno:44 +// main() +// main/files/std5_stdlibs.gno:10 + // Error: // frame not found diff --git a/gnovm/tests/files/std8_stdlibs.gno b/gnovm/tests/files/std8_stdlibs.gno index 6964cec1d3d..ab5e15bd618 100644 --- a/gnovm/tests/files/std8_stdlibs.gno +++ b/gnovm/tests/files/std8_stdlibs.gno @@ -21,5 +21,18 @@ func main() { testutils.WrapCall(inner) } +// Stacktrace: +// panic: frame not found +// callerAt(n) +// gonative:std.callerAt +// std.GetCallerAt(4) +// std/native.gno:44 +// fn() +// main/files/std8_stdlibs.gno:16 +// testutils.WrapCall(inner) +// gno.land/p/demo/testutils/misc.gno:5 +// main() +// main/files/std8_stdlibs.gno:21 + // Error: // frame not found diff --git a/gnovm/tests/files/time17_native.gno b/gnovm/tests/files/time17_native.gno new file mode 100644 index 00000000000..6733c1381cb --- /dev/null +++ b/gnovm/tests/files/time17_native.gno @@ -0,0 +1,20 @@ +package main + +import ( + "fmt" + "time" +) + +func main() { + now := time.Now() + now.In(nil) +} + +// Error: +// time: missing Location in call to Time.In + +// Stacktrace: +// now.In(gonative{*time.Location}) +// gofunction:func(*time.Location) time.Time +// main() +// main/files/time17_native.gno:10 diff --git a/gnovm/tests/files/typeassert1.gno b/gnovm/tests/files/typeassert1.gno index 041034e4bd0..f6609a3d18c 100644 --- a/gnovm/tests/files/typeassert1.gno +++ b/gnovm/tests/files/typeassert1.gno @@ -9,5 +9,10 @@ func main() { _ = a.(A) } +// Stacktrace: +// panic: interface conversion: interface is nil, not main.A +// main() +// main/files/typeassert1.gno:9 + // Error: // interface conversion: interface is nil, not main.A diff --git a/gnovm/tests/files/typeassert2a.gno b/gnovm/tests/files/typeassert2a.gno index 0441bf83437..bfbd24d38bd 100644 --- a/gnovm/tests/files/typeassert2a.gno +++ b/gnovm/tests/files/typeassert2a.gno @@ -11,5 +11,10 @@ func main() { }() } +// Stacktrace: +// panic: interface conversion: interface is nil, not main.A +// main() +// main/files/typeassert2a.gno:10 + // Error: // interface conversion: interface is nil, not main.A diff --git a/gnovm/tests/files/typeassert9.gno b/gnovm/tests/files/typeassert9.gno index d9d5bad55af..6ea072661c1 100644 --- a/gnovm/tests/files/typeassert9.gno +++ b/gnovm/tests/files/typeassert9.gno @@ -16,5 +16,10 @@ func main() { _ = reader.(Writer) } +// Stacktrace: +// panic: interface conversion: interface is nil, not main.Writer +// main() +// main/files/typeassert9.gno:16 + // Error: // interface conversion: interface is nil, not main.Writer diff --git a/gnovm/tests/files/zrealm_panic.gno b/gnovm/tests/files/zrealm_panic.gno new file mode 100644 index 00000000000..3864e2a7f7f --- /dev/null +++ b/gnovm/tests/files/zrealm_panic.gno @@ -0,0 +1,20 @@ +// PKGPATH: gno.land/r/test +package test + +type MyStruct struct{} + +func (ms MyStruct) Panic() { + panic("panic") +} + +func main() { + ms := MyStruct{} + ms.Panic() +} + +// Stacktrace: +// panic: panic +// ms.Panic() +// gno.land/r/test/main.gno:7 +// main() +// gno.land/r/test/main.gno:12