Skip to content

Commit daa6538

Browse files
committed
internal/lsp/source: fix panic in formatZeroValue for invalid type
formatZeroValue is currently only used when formatting return values for statement completion. Per golang/go#40956, it must be possible to hit this codepath with an invalid type. In this case, the empty string seems like a reasonable value. Perhaps we could do better, but fix the panic for now. Fixes golang/go#40956 Change-Id: I45b559d41001c857cef34aea2a5ac4a9096fe950 Reviewed-on: https://go-review.googlesource.com/c/tools/+/249818 Run-TryBot: Robert Findley <[email protected]> TryBot-Result: Gobot Gobot <[email protected]> Reviewed-by: Heschi Kreinick <[email protected]>
1 parent 74543c4 commit daa6538

File tree

2 files changed

+31
-2
lines changed

2 files changed

+31
-2
lines changed

internal/lsp/source/util.go

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -582,7 +582,8 @@ func prevStmt(pos token.Pos, path []ast.Node) ast.Stmt {
582582
return nil
583583
}
584584

585-
// formatZeroValue produces Go code representing the zero value of T.
585+
// formatZeroValue produces Go code representing the zero value of T. It
586+
// returns the empty string if T is invalid.
586587
func formatZeroValue(T types.Type, qf types.Qualifier) string {
587588
switch u := T.Underlying().(type) {
588589
case *types.Basic:
@@ -594,7 +595,7 @@ func formatZeroValue(T types.Type, qf types.Qualifier) string {
594595
case u.Info()&types.IsBoolean > 0:
595596
return "false"
596597
default:
597-
panic(fmt.Sprintf("unhandled basic type: %v", u))
598+
return ""
598599
}
599600
case *types.Pointer, *types.Interface, *types.Chan, *types.Map, *types.Slice, *types.Signature:
600601
return "nil"

internal/lsp/source/util_test.go

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
// Copyright 2020 The Go Authors. All rights reserved.
2+
// Use of this source code is governed by a BSD-style
3+
// license that can be found in the LICENSE file.
4+
5+
package source
6+
7+
import (
8+
"go/types"
9+
"testing"
10+
)
11+
12+
func TestFormatZeroValue(t *testing.T) {
13+
tests := []struct {
14+
typ types.Type
15+
want string
16+
}{
17+
{types.Typ[types.String], `""`},
18+
{types.Typ[types.Byte], "0"},
19+
{types.Typ[types.Invalid], ""},
20+
{types.Universe.Lookup("error").Type(), "nil"},
21+
}
22+
23+
for _, test := range tests {
24+
if got := formatZeroValue(test.typ, nil); got != test.want {
25+
t.Errorf("formatZeroValue(%v) = %q, want %q", test.typ, got, test.want)
26+
}
27+
}
28+
}

0 commit comments

Comments
 (0)