1
0
mirror of https://github.com/golang/go synced 2024-09-29 16:34:31 -06:00

go/parser: allow parsing aliases with type parameters

We already guard against this in the type checker, and it will
eventually be allowed per the accepted proposal.

Add a placeholder error code for the corresponding type checker error.

Change-Id: I5cc2f1413ecc89ec2094f7178fdb156fb8cc2e43
Reviewed-on: https://go-review.googlesource.com/c/go/+/360235
Trust: Robert Findley <rfindley@google.com>
Run-TryBot: Robert Findley <rfindley@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Robert Griesemer <gri@golang.org>
This commit is contained in:
Robert Findley 2021-10-31 11:33:00 -04:00
parent 57dc6e2475
commit 02d7eab527
3 changed files with 6 additions and 4 deletions

View File

@ -2539,9 +2539,11 @@ func (p *parser) parseGenericType(spec *ast.TypeSpec, openPos token.Pos, name0 *
list := p.parseParameterList(name0, token.RBRACK)
closePos := p.expect(token.RBRACK)
spec.TypeParams = &ast.FieldList{Opening: openPos, List: list, Closing: closePos}
// Type alias cannot have type parameters. Accept them for robustness but complain.
// Let the type checker decide whether to accept type parameters on aliases:
// see issue #46477.
if p.tok == token.ASSIGN {
p.error(p.pos, "generic type cannot be alias")
// type alias
spec.Assign = p.pos
p.next()
}
spec.Type = p.parseType()

View File

@ -123,6 +123,7 @@ var validWithTParamsOnly = []string{
`package p; type I1[T any /* ERROR "expected ']', found any" */ ] interface{}; type I2 interface{ I1[int] }`,
`package p; type I1[T any /* ERROR "expected ']', found any" */ ] interface{}; type I2[T any] interface{ I1[T] }`,
`package p; type _ interface { f[ /* ERROR "expected ';', found '\['" */ T any]() }`,
`package p; type T[P any /* ERROR "expected ']'" */ ] = T0`,
}
func TestValid(t *testing.T) {
@ -240,7 +241,6 @@ var invalidNoTParamErrs = []string{
// error messages produced when ParseTypeParams is set.
var invalidTParamErrs = []string{
`package p; type _[_ any] int; var _ = T[] /* ERROR "expected operand" */ {}`,
`package p; type T[P any] = /* ERROR "cannot be alias" */ T0`,
`package p; var _ func[ /* ERROR "cannot have type parameters" */ T any](T)`,
`package p; func _[]/* ERROR "empty type parameter list" */()`,

View File

@ -631,7 +631,7 @@ func (check *Checker) typeDecl(obj *TypeName, tdecl *ast.TypeSpec, def *Named) {
if alias && tdecl.TypeParams.NumFields() != 0 {
// The parser will ensure this but we may still get an invalid AST.
// Complain and continue as regular type definition.
check.error(atPos(tdecl.Assign), 0, "generic type cannot be alias")
check.error(atPos(tdecl.Assign), _Todo, "generic type cannot be alias")
alias = false
}