From: Robert Griesemer Date: Wed, 19 Aug 2009 23:44:04 +0000 (-0700) Subject: new scope rules X-Git-Tag: weekly.2009-11-06~827 X-Git-Url: http://www.git.cypherpunks.su/?a=commitdiff_plain;h=0a162a1433c457e2033825857c2d203835dc5119;p=gostls13.git new scope rules DELTA=137 (50 added, 24 deleted, 63 changed) OCL=33476 CL=33553 --- diff --git a/doc/go_spec.html b/doc/go_spec.html index 768084385b..7f8501375b 100644 --- a/doc/go_spec.html +++ b/doc/go_spec.html @@ -10,9 +10,7 @@ Open issues: Todo's: [ ] need language about function/method calls and parameter passing rules -[ ] clarify new scope rules for package-level identifiers -[ ] clarify scope of identifiers denoting imported packages (file scope) -[ ] package identifier not in any scope +[ ] need to say something about "scope" of selectors? [ ] clarify what a field name is in struct declarations (struct{T} vs struct {T T} vs struct {t T}) [ ] need explicit language about the result type of operations @@ -1226,74 +1224,119 @@ They will be equal only if they have the same dynamic type and the underlying va
+

Blocks

+ +

+A block is a sequence of declarations and statements within matching +brace brackets. +

+ +
+Block = "{" StatementList "}" .
+
+ +

+In addition to explicit blocks in the source code, there are implicit blocks: +

+ +
    +
  1. The universe block encompasses all Go source text.
  2. + +
  3. Each package (§Packages) has a package block containing all + Go source text for that package.
  4. + +
  5. Each file has a file block containing all Go source text + in that file.
  6. + +
  7. Each if, for, and switch + statement is considered to be in its own implicit block.
  8. + +
  9. Each case or type case clause in a switch statement, + and each communication clause in a select statement + acts as an implicit block.
  10. +
+ +

+Blocks nest and influence scoping (§Declarations and Scope). +

+ +

Declarations and Scope

-A declaration binds an identifier to a language entity such as -a variable or function and specifies properties such as its type. +A declaration binds an identifier to a constant, type, variable, function, or package. Every identifier in a program must be declared. +No identifier may be declared twice in the same block, and +no identifier may be declared in both the file and package block.

-Declaration = ConstDecl | TypeDecl | VarDecl | FunctionDecl | MethodDecl .
+Declaration   = ConstDecl | TypeDecl | VarDecl .
+TopLevelDecl  = Declaration | FunctionDecl | MethodDecl .
 

-The scope of an identifier is the extent of source text within which the -identifier denotes the bound entity. No identifier may be declared twice in a -single scope, but inner blocks can declare a new entity with the same -identifier, in which case the scope created by the outer declaration excludes -that created by the inner. +The scope of a declared identifier is the extent of source text in which +the identifier denotes the specified constant, type, variable, function, or package.

+

-There are levels of scoping in effect before each source file is compiled. -In order from outermost to innermost: +Go is lexically scoped using blocks:

+
    -
  1. The universe scope contains all predeclared identifiers.
  2. -
  3. An implicit scope contains only the package name.
  4. -
  5. The package-level scope surrounds all declarations at the - top level of the file, that is, outside the body of any - function or method. That scope is shared across all - source files within the package (§Packages), allowing - package-level identifiers to be shared between source - files.
  6. +
  7. The scope of a predeclared identifier is the universe block.
  8. + +
  9. The scope of an identifier denoting a constant, type, variable, + or function declared at top level (outside any function) is the + package block.
  10. + +
  11. The scope of an imported package identifier is the file block + of the file containing the import declaration.
  12. + +
  13. The scope of an identifier denoting a function parameter or + result variable is the function body.
  14. + +
  15. The scope of a constant or variable identifier declared + inside a function begins at the end of the ConstSpec or VarSpec + and ends at the end of the innermost containing block.
  16. + +
  17. The scope of a type identifier declared inside a function + begins immediately after the identifier in the TypeSpec + and ends at the end of the innermost containing block.

-The scope of an identifier depends on the entity declared: +An identifier declared in a block may be redeclared in an inner block. +While the identifier of the inner declaration is in scope, it denotes +the entity declared by the inner declaration.

-
    -
  1. The scope of predeclared identifiers is the universe scope.
  2. - -
  3. The scope of an identifier denoting a type, function or package - extends from the point of the identifier in the declaration - to the end of the innermost surrounding block.
  4. +

    +The package clause (§Package clause) is not a declaration; the package name +does not appear in any scope. Its purpose is to identify the files belonging +to the same package (§Packages) and to specify the default name for import +declarations. +

    -
  5. The scope of a constant or variable extends textually from - the end of its declaration to the end of the innermost - surrounding block. If the variable is declared in the - init statement of an if, for, - or switch statement, the - innermost surrounding block is the block associated - with that statement.
  6. -
  7. The scope of a parameter or result is the body of the - corresponding function.
  8. +

    Label scopes

    -
  9. The scope of a field or method is selectors for the - corresponding type containing the field or method (§Selectors).
  10. +

    +Labels are declared by labeled statements (§Labeled statements) and are +used in the break, continue, and goto +statements (§Break statements, §Continue statements, §Goto statements). +In contrast to other identifiers, labels are not block scoped and do +not conflict with identifiers that are not labels. The scope of a label +is the body of the function in which it is declared and excludes +the body of any nested function. +

    -
  11. The scope of a label is a special scope emcompassing - the body of the innermost surrounding function, excluding - nested functions. Labels do not conflict with non-label identifiers.
  12. -

Predeclared identifiers

-The following identifiers are implicitly declared in the outermost scope: +The following identifiers are implicitly declared in the universe block:

 Basic types:
@@ -1593,7 +1636,8 @@ A function declaration binds an identifier to a function (§Function types).
 

-FunctionDecl = "func" identifier Signature [ Block ] .
+FunctionDecl = "func" identifier Signature [ Body ] .
+Body         = Block.
 

@@ -1612,10 +1656,6 @@ func min(x int, y int) int { func flushICache(begin, end uintptr) // implemented externally

-

-Implementation restriction: Functions can only be declared at the package level. -

-

Method declarations

@@ -1623,7 +1663,7 @@ A method declaration binds an identifier to a method, which is a function with a receiver.

-MethodDecl = "func" Receiver identifier Signature [ Block ] .
+MethodDecl = "func" Receiver identifier Signature [ Body ] .
 Receiver = "(" [ identifier ] [ "*" ] TypeName ")" .
 
@@ -1664,10 +1704,6 @@ its identifier may be omitted in the declaration. The same applies in general to parameters of functions and methods.

-

-Implementation restriction: They can only be declared at package level. -

-

The type of a method is the type of a function with the receiver as first argument. For instance, the method Scale has type @@ -1918,8 +1954,7 @@ It consists of a specification of the function type and a function body.

-FunctionLit   = FunctionType Block .
-Block         = "{" StatementList "}" .
+FunctionLit = FunctionType Body .
 
@@ -3218,10 +3253,7 @@ indicate that control should flow from the end of this clause to
 the first statement of the next clause.
 Otherwise control flows to the end of the "switch" statement.
 

-

-Each case clause acts as a block for scoping purposes -(§Declarations and scope rules). -

+

A "switch" statement may include a simple statement before the expression. @@ -3505,10 +3537,6 @@ SendExpr = Expression "<-" Expression . RecvExpr = [ Expression ( "=" | ":=" ) ] "<-" Expression .

-

-Each communication clause acts as a block for the purpose of scoping -(§Declarations and scope rules). -

For all the send and receive expressions in the "select" statement, the channel expression is evaluated. Any expressions @@ -3973,13 +4001,11 @@ Each source file consists of a package clause defining the package to which it belongs, followed by a possibly empty set of import declarations that declare packages whose contents it wishes to use, followed by a possibly empty set of declarations of functions, -types, variables, and constants. The source text following the -package clause acts as a block for scoping (§Declarations and scope -rules). +types, variables, and constants.

-SourceFile       = PackageClause { ImportDecl [ ";" ] } { Declaration [ ";" ] } .
+SourceFile       = PackageClause { ImportDecl [ ";" ] } { TopLevelDecl [ ";" ] } .
 

Package clause

@@ -4002,7 +4028,7 @@ A set of files sharing the same PackageName form the implementation of a package An implementation may require that all source files for a package inhabit the same directory.

-

Import

+

Import declarations

A source file gains access to exported identifiers (§Exported