}
 
 // stmtContext is a bitset describing which
-// control-flow statements are permissible.
+// control-flow statements are permissible,
+// and provides additional context information
+// for better error messages.
 type stmtContext uint
 
 const (
+       // permissible control-flow statements
        breakOk stmtContext = 1 << iota
        continueOk
        fallthroughOk
+
+       // additional context information
+       finalSwitchCase
 )
 
 func (check *Checker) simpleStmt(s ast.Stmt) {
                }(check.scope)
        }
 
-       inner := ctxt &^ fallthroughOk
+       inner := ctxt &^ (fallthroughOk | finalSwitchCase)
        switch s := s.(type) {
        case *ast.BadStmt, *ast.EmptyStmt:
                // ignore
                        }
                case token.FALLTHROUGH:
                        if ctxt&fallthroughOk == 0 {
-                               check.error(s.Pos(), "fallthrough statement out of place")
+                               msg := "fallthrough statement out of place"
+                               if ctxt&finalSwitchCase != 0 {
+                                       msg = "cannot fallthrough final case in switch"
+                               }
+                               check.error(s.Pos(), msg)
                        }
                default:
                        check.invalidAST(s.Pos(), "branch statement: %s", s.Tok)
                        inner := inner
                        if i+1 < len(s.Body.List) {
                                inner |= fallthroughOk
+                       } else {
+                               inner |= finalSwitchCase
                        }
                        check.stmtList(inner, clause.Body)
                        check.closeScope()
 
        default:
                fallthrough; ;
        case 4:
-               fallthrough /* ERROR "fallthrough statement out of place" */
+               fallthrough /* ERROR "cannot fallthrough final case in switch" */
        }
 
        var y interface{}
                goto L6
                goto L7
                goto L8
-               L6: L7: L8: fallthrough /* ERROR "fallthrough statement out of place" */
+               L6: L7: L8: fallthrough /* ERROR "cannot fallthrough final case in switch" */
        }
 
        switch x {
                fallthrough /* ERROR "fallthrough statement out of place" */
                { /* empty block is not an empty statement */ }; ;
        default:
+               fallthrough /* ERROR "cannot fallthrough final case in switch" */
+       }
+
+       switch x {
+       case 0:
+               {
+                       fallthrough /* ERROR "fallthrough statement out of place" */
+               }
        }
 }