case *syntax.ReturnStmt:
res := check.sig.results
+ // Return with implicit results allowed for function with named results.
+ // (If one is named, all are named.)
results := unpackExpr(s.Results)
- if res.Len() > 0 {
- // function returns results
- // (if one, say the first, result parameter is named, all of them are named)
- if len(results) == 0 && res.vars[0].name != "" {
- // spec: "Implementation restriction: A compiler may disallow an empty expression
- // list in a "return" statement if a different entity (constant, type, or variable)
- // with the same name as a result parameter is in scope at the place of the return."
- for _, obj := range res.vars {
- if alt := check.lookup(obj.name); alt != nil && alt != obj {
- var err error_
- err.errorf(s, "result parameter %s not in scope at return", obj.name)
- err.errorf(alt, "inner declaration of %s", obj)
- check.report(&err)
- // ok to continue
- }
+ if len(results) == 0 && res.Len() > 0 && res.vars[0].name != "" {
+ // spec: "Implementation restriction: A compiler may disallow an empty expression
+ // list in a "return" statement if a different entity (constant, type, or variable)
+ // with the same name as a result parameter is in scope at the place of the return."
+ for _, obj := range res.vars {
+ if alt := check.lookup(obj.name); alt != nil && alt != obj {
+ var err error_
+ err.errorf(s, "result parameter %s not in scope at return", obj.name)
+ err.errorf(alt, "inner declaration of %s", obj)
+ check.report(&err)
+ // ok to continue
}
- } else {
- // return has results or result parameters are unnamed
- check.initVars(res.vars, results, s)
}
- } else if len(results) > 0 {
- check.error(results[0], "no result values expected")
- check.use(results...)
+ } else {
+ var lhs []*Var
+ if res.Len() > 0 {
+ lhs = res.vars
+ }
+ check.initVars(lhs, results, s)
}
case *syntax.BranchStmt:
func returns0() {
return
- return 0 /* ERROR no result values expected */
+ return 0 /* ERROR too many return values */
}
func returns1(x float64) (int, *float64) {
func _() {
var x int
- return x /* ERROR no result values expected */
- return math /* ERROR no result values expected */ .Sin(0)
+ return x /* ERROR too many return values */
+ return math /* ERROR too many return values */ .Sin(0)
}
func _() int {
case *ast.ReturnStmt:
res := check.sig.results
- if res.Len() > 0 {
- // function returns results
- // (if one, say the first, result parameter is named, all of them are named)
- if len(s.Results) == 0 && res.vars[0].name != "" {
- // spec: "Implementation restriction: A compiler may disallow an empty expression
- // list in a "return" statement if a different entity (constant, type, or variable)
- // with the same name as a result parameter is in scope at the place of the return."
- for _, obj := range res.vars {
- if alt := check.lookup(obj.name); alt != nil && alt != obj {
- check.errorf(s, _OutOfScopeResult, "result parameter %s not in scope at return", obj.name)
- check.errorf(alt, _OutOfScopeResult, "\tinner declaration of %s", obj)
- // ok to continue
- }
+ // Return with implicit results allowed for function with named results.
+ // (If one is named, all are named.)
+ if len(s.Results) == 0 && res.Len() > 0 && res.vars[0].name != "" {
+ // spec: "Implementation restriction: A compiler may disallow an empty expression
+ // list in a "return" statement if a different entity (constant, type, or variable)
+ // with the same name as a result parameter is in scope at the place of the return."
+ for _, obj := range res.vars {
+ if alt := check.lookup(obj.name); alt != nil && alt != obj {
+ check.errorf(s, _OutOfScopeResult, "result parameter %s not in scope at return", obj.name)
+ check.errorf(alt, _OutOfScopeResult, "\tinner declaration of %s", obj)
+ // ok to continue
}
- } else {
- // return has results or result parameters are unnamed
- check.initVars(res.vars, s.Results, s)
}
- } else if len(s.Results) > 0 {
- check.error(s.Results[0], _WrongResultCount, "no result values expected")
- check.use(s.Results...)
+ } else {
+ var lhs []*Var
+ if res.Len() > 0 {
+ lhs = res.vars
+ }
+ check.initVars(lhs, s.Results, s)
}
case *ast.BranchStmt:
func returns0() {
return
- return 0 /* ERROR no result values expected */
+ return 0 /* ERROR too many return values */
}
func returns1(x float64) (int, *float64) {
func _() {
var x int
- return x /* ERROR no result values expected */
- return math /* ERROR no result values expected */ .Sin(0)
+ return x /* ERROR too many return values */
+ return math /* ERROR too many return values */ .Sin(0)
}
func _() int {
}
func foo2() {
- return int(2), 2 // ERROR "too many arguments to return\n\thave \(int, number\)\n\twant \(\)|return with value in function with no return type|no result values expected"
+ return int(2), 2 // ERROR "too many (arguments to return|return values)\n\thave \(int, number\)\n\twant \(\)|return with value in function with no return type"
}
func foo3(v int) (a, b, c, d int) {
}
func _() {
- return 1 // ERROR "too many arguments to return\n\thave \(number\)\n\twant \(\)|no result values expected"
+ return 1 // ERROR "too many (arguments to return|return values)\n\thave \(number\)\n\twant \(\)"
}