diff --git a/gopls/internal/analysis/fillstruct/fillstruct.go b/gopls/internal/analysis/fillstruct/fillstruct.go index 1230a87ff44..4b1bb4aa4b0 100644 --- a/gopls/internal/analysis/fillstruct/fillstruct.go +++ b/gopls/internal/analysis/fillstruct/fillstruct.go @@ -345,6 +345,8 @@ func indent(str, ind []byte) []byte { // // The reasoning here is that users will call fillstruct with the intention of // initializing the struct, in which case setting these fields to nil has no effect. +// +// populateValue returns nil if the value cannot be filled. func populateValue(f *ast.File, pkg *types.Package, typ types.Type) ast.Expr { switch u := typ.Underlying().(type) { case *types.Basic: @@ -357,6 +359,8 @@ func populateValue(f *ast.File, pkg *types.Package, typ types.Type) ast.Expr { return &ast.BasicLit{Kind: token.STRING, Value: `""`} case u.Kind() == types.UnsafePointer: return ast.NewIdent("nil") + case u.Kind() == types.Invalid: + return nil default: panic(fmt.Sprintf("unknown basic type %v", u)) } @@ -478,9 +482,13 @@ func populateValue(f *ast.File, pkg *types.Package, typ types.Type) ast.Expr { }, } default: + x := populateValue(f, pkg, u.Elem()) + if x == nil { + return nil + } return &ast.UnaryExpr{ Op: token.AND, - X: populateValue(f, pkg, u.Elem()), + X: x, } } diff --git a/gopls/internal/test/marker/testdata/codeaction/fill_struct.txt b/gopls/internal/test/marker/testdata/codeaction/fill_struct.txt index 4e798a55fd6..092a4275ffb 100644 --- a/gopls/internal/test/marker/testdata/codeaction/fill_struct.txt +++ b/gopls/internal/test/marker/testdata/codeaction/fill_struct.txt @@ -558,3 +558,17 @@ func _[T any]() { + _ = S{ + t: *new(T), + } //@codeactionedit("}", "refactor.rewrite", typeparams5) +-- issue63921.go -- +package fillstruct + +// Test for golang/go#63921: fillstruct panicked with invalid fields. +type invalidStruct struct { + F int + Undefined +} + +func _() { + // Note: the golden content for issue63921 is empty: fillstruct produces no + // edits, but does not panic. + invalidStruct{} //@codeactionedit("}", "refactor.rewrite", issue63921) +}