]> Cypherpunks.ru repositories - gostls13.git/commitdiff
go/types, types2: rename Environment to Context
authorRobert Findley <rfindley@google.com>
Wed, 29 Sep 2021 13:35:02 +0000 (09:35 -0400)
committerRobert Findley <rfindley@google.com>
Wed, 29 Sep 2021 17:06:53 +0000 (17:06 +0000)
Replace the name Environment with Context, as discussed in #47916. Along
the way, fix some stale or inaccurate comments.

The Environment type remains temporarily as an alias for Context, to
allow the x/tools Trybot to pass until dependency on types.Environment
can be removed.

Updates #47916

Change-Id: Iffd069ab0e8adebf4207c8f8891468a64d32b7cc
Reviewed-on: https://go-review.googlesource.com/c/go/+/353089
Trust: Robert Findley <rfindley@google.com>
Run-TryBot: Robert Findley <rfindley@google.com>
Reviewed-by: Robert Griesemer <gri@golang.org>
TryBot-Result: Go Bot <gobot@golang.org>

26 files changed:
src/cmd/compile/internal/noder/import.go
src/cmd/compile/internal/noder/irgen.go
src/cmd/compile/internal/noder/reader2.go
src/cmd/compile/internal/noder/unified.go
src/cmd/compile/internal/types2/api.go
src/cmd/compile/internal/types2/check.go
src/cmd/compile/internal/types2/context.go [moved from src/cmd/compile/internal/types2/environment.go with 67% similarity]
src/cmd/compile/internal/types2/decl.go
src/cmd/compile/internal/types2/instantiate.go
src/cmd/compile/internal/types2/instantiate_test.go
src/cmd/compile/internal/types2/named.go
src/cmd/compile/internal/types2/object.go
src/cmd/compile/internal/types2/signature.go
src/cmd/compile/internal/types2/subst.go
src/cmd/compile/internal/types2/typestring.go
src/go/types/api.go
src/go/types/check.go
src/go/types/context.go [moved from src/go/types/environment.go with 65% similarity]
src/go/types/decl.go
src/go/types/instantiate.go
src/go/types/instantiate_test.go
src/go/types/named.go
src/go/types/object.go
src/go/types/signature.go
src/go/types/subst.go
src/go/types/typestring.go

index f13f8ca7f5ef7eb8dadef5a125cf797f901203a8..f065c97763d60257ad7d53778f37e843fdb684f5 100644 (file)
@@ -43,12 +43,12 @@ var haveLegacyImports = false
 // for an imported package by overloading writeNewExportFunc, then
 // that payload will be mapped into memory and passed to
 // newReadImportFunc.
-var newReadImportFunc = func(data string, pkg1 *types.Pkg, env *types2.Environment, packages map[string]*types2.Package) (pkg2 *types2.Package, err error) {
+var newReadImportFunc = func(data string, pkg1 *types.Pkg, env *types2.Context, packages map[string]*types2.Package) (pkg2 *types2.Package, err error) {
        panic("unexpected new export data payload")
 }
 
 type gcimports struct {
-       env      *types2.Environment
+       env      *types2.Context
        packages map[string]*types2.Package
 }
 
@@ -224,7 +224,7 @@ func parseImportPath(pathLit *syntax.BasicLit) (string, error) {
 // readImportFile reads the import file for the given package path and
 // returns its types.Pkg representation. If packages is non-nil, the
 // types2.Package representation is also returned.
-func readImportFile(path string, target *ir.Package, env *types2.Environment, packages map[string]*types2.Package) (pkg1 *types.Pkg, pkg2 *types2.Package, err error) {
+func readImportFile(path string, target *ir.Package, env *types2.Context, packages map[string]*types2.Package) (pkg1 *types.Pkg, pkg2 *types2.Package, err error) {
        path, err = resolveImportPath(path)
        if err != nil {
                return
index c1a4f30f4ac4a4e618f93bc222d688013fb9ae36..6a09c2ee0c0a030232213f53c96dc75b680e9dc3 100644 (file)
@@ -34,13 +34,13 @@ func checkFiles(noders []*noder) (posMap, *types2.Package, *types2.Info) {
        }
 
        // typechecking
-       env := types2.NewEnvironment()
+       env := types2.NewContext()
        importer := gcimports{
                env:      env,
                packages: map[string]*types2.Package{"unsafe": types2.Unsafe},
        }
        conf := types2.Config{
-               Environment:           env,
+               Context:               env,
                GoVersion:             base.Flag.Lang,
                IgnoreLabels:          true, // parser already checked via syntax.CheckBranches mode
                CompilerErrorMessages: true, // use error strings matching existing compiler errors
index dcd9a65f404a39f21be6470e5b4e42be9bccf85f..de7211305b7bfe09d6699346756953e62021a481 100644 (file)
@@ -16,7 +16,7 @@ import (
 type pkgReader2 struct {
        pkgDecoder
 
-       env     *types2.Environment
+       env     *types2.Context
        imports map[string]*types2.Package
 
        posBases []*syntax.PosBase
@@ -24,7 +24,7 @@ type pkgReader2 struct {
        typs     []types2.Type
 }
 
-func readPackage2(env *types2.Environment, imports map[string]*types2.Package, input pkgDecoder) *types2.Package {
+func readPackage2(env *types2.Context, imports map[string]*types2.Package, input pkgDecoder) *types2.Package {
        pr := pkgReader2{
                pkgDecoder: input,
 
index 3d4650a01f671381e5f164d4f84dcf6fe0ee56be..ee76ff34af451369910927182119512d17399ef7 100644 (file)
@@ -78,7 +78,7 @@ func unified(noders []*noder) {
                base.Errorf("cannot use -G and -d=quirksmode together")
        }
 
-       newReadImportFunc = func(data string, pkg1 *types.Pkg, env *types2.Environment, packages map[string]*types2.Package) (pkg2 *types2.Package, err error) {
+       newReadImportFunc = func(data string, pkg1 *types.Pkg, env *types2.Context, packages map[string]*types2.Package) (pkg2 *types2.Package, err error) {
                pr := newPkgDecoder(pkg1.Path, data)
 
                // Read package descriptors for both types2 and compiler backend.
index b0e86357b70f1e790a43814364ea8e14b6fe28be..faf570c32e812354d169a90ef14526f94d1d5b6b 100644 (file)
@@ -108,10 +108,9 @@ type ImporterFrom interface {
 // A Config specifies the configuration for type checking.
 // The zero value for Config is a ready-to-use default configuration.
 type Config struct {
-       // Environment is the environment used for resolving global
-       // identifiers. If nil, the type checker will initialize this
-       // field with a newly created environment.
-       Environment *Environment
+       // Context is the context used for resolving global identifiers. If nil, the
+       // type checker will initialize this field with a newly created context.
+       Context *Context
 
        // GoVersion describes the accepted Go language version. The string
        // must follow the format "go%d.%d" (e.g. "go1.12") or ist must be
index e45598e0ef1af40d8a8895c2467ebc7fb757cb40..5957518c171bdf277dc606a1d48e48161b1dcbb2 100644 (file)
@@ -170,9 +170,9 @@ func NewChecker(conf *Config, pkg *Package, info *Info) *Checker {
                conf = new(Config)
        }
 
-       // make sure we have an environment
-       if conf.Environment == nil {
-               conf.Environment = NewEnvironment()
+       // make sure we have a context
+       if conf.Context == nil {
+               conf.Context = NewContext()
        }
 
        // make sure we have an info struct
similarity index 67%
rename from src/cmd/compile/internal/types2/environment.go
rename to src/cmd/compile/internal/types2/context.go
index fe9a3099fee13944d09196b29a5e292ed7b0e641..a8f859124387a99ba3ed43304d5db61761bb6d5b 100644 (file)
@@ -9,21 +9,21 @@ import (
        "sync"
 )
 
-// An Environment is an opaque type checking environment. It may be used to
-// share identical type instances across type-checked packages or calls to
+// An Context is an opaque type checking context. It may be used to share
+// identical type instances across type-checked packages or calls to
 // Instantiate.
 //
 // It is safe for concurrent use.
-type Environment struct {
+type Context struct {
        mu      sync.Mutex
        typeMap map[string]*Named // type hash -> instance
        nextID  int               // next unique ID
        seen    map[*Named]int    // assigned unique IDs
 }
 
-// NewEnvironment creates a new Environment.
-func NewEnvironment() *Environment {
-       return &Environment{
+// NewContext creates a new Context.
+func NewContext() *Context {
+       return &Context{
                typeMap: make(map[string]*Named),
                seen:    make(map[*Named]int),
        }
@@ -33,12 +33,12 @@ func NewEnvironment() *Environment {
 // type hash: types that are identical produce identical string representations.
 // If typ is a *Named type and targs is not empty, typ is printed as if it were
 // instantiated with targs. The result is guaranteed to not contain blanks (" ").
-func (env *Environment) TypeHash(typ Type, targs []Type) string {
-       assert(env != nil)
+func (ctxt *Context) TypeHash(typ Type, targs []Type) string {
+       assert(ctxt != nil)
        assert(typ != nil)
        var buf bytes.Buffer
 
-       h := newTypeHasher(&buf, env)
+       h := newTypeHasher(&buf, ctxt)
        if named, _ := typ.(*Named); named != nil && len(targs) > 0 {
                // Don't use WriteType because we need to use the provided targs
                // and not any targs that might already be with the *Named type.
@@ -55,27 +55,27 @@ func (env *Environment) TypeHash(typ Type, targs []Type) string {
 
 // typeForHash returns the recorded type for the type hash h, if it exists.
 // If no type exists for h and n is non-nil, n is recorded for h.
-func (env *Environment) typeForHash(h string, n *Named) *Named {
-       env.mu.Lock()
-       defer env.mu.Unlock()
-       if existing := env.typeMap[h]; existing != nil {
+func (ctxt *Context) typeForHash(h string, n *Named) *Named {
+       ctxt.mu.Lock()
+       defer ctxt.mu.Unlock()
+       if existing := ctxt.typeMap[h]; existing != nil {
                return existing
        }
        if n != nil {
-               env.typeMap[h] = n
+               ctxt.typeMap[h] = n
        }
        return n
 }
 
 // idForType returns a unique ID for the pointer n.
-func (env *Environment) idForType(n *Named) int {
-       env.mu.Lock()
-       defer env.mu.Unlock()
-       id, ok := env.seen[n]
+func (ctxt *Context) idForType(n *Named) int {
+       ctxt.mu.Lock()
+       defer ctxt.mu.Unlock()
+       id, ok := ctxt.seen[n]
        if !ok {
-               id = env.nextID
-               env.seen[n] = id
-               env.nextID++
+               id = ctxt.nextID
+               ctxt.seen[n] = id
+               ctxt.nextID++
        }
        return id
 }
index 326763d9b79350ec1c48e250ba6618ff1de216e0..128e89dec65d7f2ecc9afe2d1e730764f6bff801 100644 (file)
@@ -69,7 +69,7 @@ func (check *Checker) objDecl(obj Object, def *Named) {
        // Funcs with m.instRecv set have not yet be completed. Complete them now
        // so that they have a type when objDecl exits.
        if m, _ := obj.(*Func); m != nil && m.instRecv != nil {
-               check.completeMethod(check.conf.Environment, m)
+               check.completeMethod(check.conf.Context, m)
        }
 
        // Checking the declaration of obj means inferring its type
@@ -330,7 +330,7 @@ func (check *Checker) validType(typ Type, path []Object) typeInfo {
                }
 
        case *Named:
-               t.resolve(check.conf.Environment)
+               t.resolve(check.conf.Context)
 
                // don't touch the type if it is from a different package or the Universe scope
                // (doing so would lead to a race condition - was issue #35049)
index 7a9279943c190f0f93af895b649b8914e0e5645f..5da371f201bdbad03ae5fc5b45162ddf4019d9bd 100644 (file)
@@ -20,9 +20,8 @@ import (
 // *Signature). Any methods attached to a *Named are simply copied; they are
 // not instantiated.
 //
-// If env is non-nil, it may be used to de-dupe the instance against previous
-// instances with the same identity. This functionality is implemented for
-// environments with non-nil Checkers.
+// If ctxt is non-nil, it may be used to de-dupe the instance against previous
+// instances with the same identity.
 //
 // If verify is set and constraint satisfaction fails, the returned error may
 // be of dynamic type ArgumentError indicating which type argument did not
@@ -30,8 +29,8 @@ import (
 //
 // TODO(rfindley): change this function to also return an error if lengths of
 // tparams and targs do not match.
-func Instantiate(env *Environment, typ Type, targs []Type, validate bool) (Type, error) {
-       inst := (*Checker)(nil).instance(nopos, typ, targs, env)
+func Instantiate(ctxt *Context, typ Type, targs []Type, validate bool) (Type, error) {
+       inst := (*Checker)(nil).instance(nopos, typ, targs, ctxt)
 
        var err error
        if validate {
@@ -71,7 +70,7 @@ func (check *Checker) instantiate(pos syntax.Pos, typ Type, targs []Type, posLis
                }()
        }
 
-       inst := check.instance(pos, typ, targs, check.conf.Environment)
+       inst := check.instance(pos, typ, targs, check.conf.Context)
 
        assert(len(posList) <= len(targs))
        check.later(func() {
@@ -103,28 +102,28 @@ func (check *Checker) instantiate(pos syntax.Pos, typ Type, targs []Type, posLis
 // instance creates a type or function instance using the given original type
 // typ and arguments targs. For Named types the resulting instance will be
 // unexpanded.
-func (check *Checker) instance(pos syntax.Pos, typ Type, targs []Type, env *Environment) Type {
+func (check *Checker) instance(pos syntax.Pos, typ Type, targs []Type, ctxt *Context) Type {
        switch t := typ.(type) {
        case *Named:
                var h string
-               if env != nil {
-                       h = env.TypeHash(t, targs)
+               if ctxt != nil {
+                       h = ctxt.TypeHash(t, targs)
                        // typ may already have been instantiated with identical type arguments. In
                        // that case, re-use the existing instance.
-                       if named := env.typeForHash(h, nil); named != nil {
+                       if named := ctxt.typeForHash(h, nil); named != nil {
                                return named
                        }
                }
                tname := NewTypeName(pos, t.obj.pkg, t.obj.name, nil)
                named := check.newNamed(tname, t, nil, nil, nil) // methods and tparams are set when named is resolved
                named.targs = NewTypeList(targs)
-               named.resolver = func(env *Environment, n *Named) (*TypeParamList, Type, []*Func) {
-                       return expandNamed(env, n, pos)
+               named.resolver = func(ctxt *Context, n *Named) (*TypeParamList, Type, []*Func) {
+                       return expandNamed(ctxt, n, pos)
                }
-               if env != nil {
-                       // It's possible that we've lost a race to add named to the environment.
-                       // In this case, use whichever instance is recorded in the environment.
-                       named = env.typeForHash(h, named)
+               if ctxt != nil {
+                       // It's possible that we've lost a race to add named to the context.
+                       // In this case, use whichever instance is recorded in the context.
+                       named = ctxt.typeForHash(h, named)
                }
                return named
 
@@ -136,7 +135,7 @@ func (check *Checker) instance(pos syntax.Pos, typ Type, targs []Type, env *Envi
                if tparams.Len() == 0 {
                        return typ // nothing to do (minor optimization)
                }
-               sig := check.subst(pos, typ, makeSubstMap(tparams.list(), targs), env).(*Signature)
+               sig := check.subst(pos, typ, makeSubstMap(tparams.list(), targs), ctxt).(*Signature)
                // If the signature doesn't use its type parameters, subst
                // will not make a copy. In that case, make a copy now (so
                // we can set tparams to nil w/o causing side-effects).
@@ -192,7 +191,7 @@ func (check *Checker) satisfies(pos syntax.Pos, targ Type, tpar *TypeParam, smap
 
        // TODO(rfindley): it would be great if users could pass in a qualifier here,
        // rather than falling back to verbose qualification. Maybe this can be part
-       // of a the shared environment.
+       // of the shared context.
        var qf Qualifier
        if check != nil {
                qf = check.qualifier
index 5d37f29b6bddeca1a4e93934b881f78f3888741d..a99fc5d032493005546c4757b38b60c39765d420 100644 (file)
@@ -18,12 +18,12 @@ func TestInstantiateEquality(t *testing.T) {
        T := pkg.Scope().Lookup("T").Type().(*Named)
        // Instantiating the same type twice should result in pointer-equivalent
        // instances.
-       env := NewEnvironment()
-       res1, err := Instantiate(env, T, []Type{Typ[Int]}, false)
+       ctxt := NewContext()
+       res1, err := Instantiate(ctxt, T, []Type{Typ[Int]}, false)
        if err != nil {
                t.Fatal(err)
        }
-       res2, err := Instantiate(env, T, []Type{Typ[Int]}, false)
+       res2, err := Instantiate(ctxt, T, []Type{Typ[Int]}, false)
        if err != nil {
                t.Fatal(err)
        }
@@ -42,15 +42,15 @@ func TestInstantiateNonEquality(t *testing.T) {
                t.Fatal(err)
        }
        // We consider T1 and T2 to be distinct types, so their instances should not
-       // be deduplicated by the environment.
+       // be deduplicated by the context.
        T1 := pkg1.Scope().Lookup("T").Type().(*Named)
        T2 := pkg2.Scope().Lookup("T").Type().(*Named)
-       env := NewEnvironment()
-       res1, err := Instantiate(env, T1, []Type{Typ[Int]}, false)
+       ctxt := NewContext()
+       res1, err := Instantiate(ctxt, T1, []Type{Typ[Int]}, false)
        if err != nil {
                t.Fatal(err)
        }
-       res2, err := Instantiate(env, T2, []Type{Typ[Int]}, false)
+       res2, err := Instantiate(ctxt, T2, []Type{Typ[Int]}, false)
        if err != nil {
                t.Fatal(err)
        }
index bc4d4f89c52547d1c084ea0a3ec5c4d8286b73de..3971e03179381d9b3d0cb34a86fa2c13b60de96d 100644 (file)
@@ -22,7 +22,7 @@ type Named struct {
        methods    []*Func        // methods declared for this type (not the method set of this type); signatures are type-checked lazily
 
        // resolver may be provided to lazily resolve type parameters, underlying, and methods.
-       resolver func(*Environment, *Named) (tparams *TypeParamList, underlying Type, methods []*Func)
+       resolver func(*Context, *Named) (tparams *TypeParamList, underlying Type, methods []*Func)
        once     sync.Once // ensures that tparams, underlying, and methods are resolved before accessing
 }
 
@@ -36,7 +36,7 @@ func NewNamed(obj *TypeName, underlying Type, methods []*Func) *Named {
        return (*Checker)(nil).newNamed(obj, nil, underlying, nil, methods)
 }
 
-func (t *Named) resolve(env *Environment) *Named {
+func (t *Named) resolve(ctxt *Context) *Named {
        if t.resolver == nil {
                return t
        }
@@ -50,7 +50,7 @@ func (t *Named) resolve(env *Environment) *Named {
                // methods would need to support reentrant calls though. It would
                // also make the API more future-proof towards further extensions
                // (like SetTypeParams).
-               t.tparams, t.underlying, t.methods = t.resolver(env, t)
+               t.tparams, t.underlying, t.methods = t.resolver(ctxt, t)
                t.fromRHS = t.underlying // for cycle detection
        })
        return t
@@ -217,37 +217,37 @@ func (n *Named) setUnderlying(typ Type) {
        }
 }
 
-// bestEnv returns the best available environment. In order of preference:
-// - the given env, if non-nil
-// - the Checker env, if check is non-nil
-// - a new environment
-func (check *Checker) bestEnv(env *Environment) *Environment {
-       if env != nil {
-               return env
+// bestContext returns the best available context. In order of preference:
+// - the given ctxt, if non-nil
+// - check.Config.Context, if check is non-nil
+// - a new Context
+func (check *Checker) bestContext(ctxt *Context) *Context {
+       if ctxt != nil {
+               return ctxt
        }
        if check != nil {
-               assert(check.conf.Environment != nil)
-               return check.conf.Environment
+               assert(check.conf.Context != nil)
+               return check.conf.Context
        }
-       return NewEnvironment()
+       return NewContext()
 }
 
 // expandNamed ensures that the underlying type of n is instantiated.
 // The underlying type will be Typ[Invalid] if there was an error.
-func expandNamed(env *Environment, n *Named, instPos syntax.Pos) (tparams *TypeParamList, underlying Type, methods []*Func) {
-       n.orig.resolve(env)
+func expandNamed(ctxt *Context, n *Named, instPos syntax.Pos) (tparams *TypeParamList, underlying Type, methods []*Func) {
+       n.orig.resolve(ctxt)
 
        check := n.check
 
        if check.validateTArgLen(instPos, n.orig.tparams.Len(), n.targs.Len()) {
-               // We must always have an env, to avoid infinite recursion.
-               env = check.bestEnv(env)
-               h := env.TypeHash(n.orig, n.targs.list())
+               // We must always have a context, to avoid infinite recursion.
+               ctxt = check.bestContext(ctxt)
+               h := ctxt.TypeHash(n.orig, n.targs.list())
                // ensure that an instance is recorded for h to avoid infinite recursion.
-               env.typeForHash(h, n)
+               ctxt.typeForHash(h, n)
 
                smap := makeSubstMap(n.orig.tparams.list(), n.targs.list())
-               underlying = n.check.subst(instPos, n.orig.underlying, smap, env)
+               underlying = n.check.subst(instPos, n.orig.underlying, smap, ctxt)
 
                for i := 0; i < n.orig.NumMethods(); i++ {
                        origm := n.orig.Method(i)
@@ -272,7 +272,7 @@ func expandNamed(env *Environment, n *Named, instPos syntax.Pos) (tparams *TypeP
        completeMethods := func() {
                for _, m := range methods {
                        if m.instRecv != nil {
-                               check.completeMethod(env, m)
+                               check.completeMethod(ctxt, m)
                        }
                }
        }
@@ -285,7 +285,7 @@ func expandNamed(env *Environment, n *Named, instPos syntax.Pos) (tparams *TypeP
        return n.orig.tparams, underlying, methods
 }
 
-func (check *Checker) completeMethod(env *Environment, m *Func) {
+func (check *Checker) completeMethod(ctxt *Context, m *Func) {
        assert(m.instRecv != nil)
        rbase := m.instRecv
        m.instRecv = nil
@@ -306,7 +306,7 @@ func (check *Checker) completeMethod(env *Environment, m *Func) {
        }
 
        smap := makeSubstMap(origSig.RecvTypeParams().list(), rbase.targs.list())
-       sig := check.subst(orig.pos, origSig, smap, env).(*Signature)
+       sig := check.subst(orig.pos, origSig, smap, ctxt).(*Signature)
        if sig == origSig {
                // No substitution occurred, but we still need to create a new signature to
                // hold the instantiated receiver.
index 2e1cd7bff13e57026f5beff7ec936557ad172cac..affeaf61f2c0bc899c9f6b3364c66e9401d41489 100644 (file)
@@ -281,7 +281,7 @@ func NewTypeName(pos syntax.Pos, pkg *Package, name string, typ Type) *TypeName
 func NewTypeNameLazy(pos syntax.Pos, pkg *Package, name string, load func(named *Named) (tparams []*TypeParam, underlying Type, methods []*Func)) *TypeName {
        obj := NewTypeName(pos, pkg, name, nil)
 
-       resolve := func(_ *Environment, t *Named) (*TypeParamList, Type, []*Func) {
+       resolve := func(_ *Context, t *Named) (*TypeParamList, Type, []*Func) {
                tparams, underlying, methods := load(t)
 
                switch underlying.(type) {
index a5348b3b14f0a5abac549a029a634bdb73c4133a..803dd8e5e7227ea0887e8447a5705030b35d7a5a 100644 (file)
@@ -234,7 +234,7 @@ func (check *Checker) funcType(sig *Signature, recvPar *syntax.Field, tparams []
                        var err string
                        switch T := rtyp.(type) {
                        case *Named:
-                               T.resolve(check.conf.Environment)
+                               T.resolve(check.conf.Context)
                                // The receiver type may be an instantiated type referred to
                                // by an alias (which cannot have receiver parameters for now).
                                if T.TypeArgs() != nil && sig.RecvTypeParams() == nil {
index 5e057a6f8059fdf83be261b540767369cf265102..a5ebd416aabf08d1bc1e30c0f45a8d6b5420adca 100644 (file)
@@ -37,8 +37,8 @@ func (m substMap) lookup(tpar *TypeParam) Type {
 // incoming type. If a substitution took place, the result type is different
 // from the incoming type.
 //
-// If the given environment is non-nil, it is used in lieu of check.env.
-func (check *Checker) subst(pos syntax.Pos, typ Type, smap substMap, env *Environment) Type {
+// If the given context is non-nil, it is used in lieu of check.Config.Context.
+func (check *Checker) subst(pos syntax.Pos, typ Type, smap substMap, ctxt *Context) Type {
        if smap.empty() {
                return typ
        }
@@ -56,7 +56,7 @@ func (check *Checker) subst(pos syntax.Pos, typ Type, smap substMap, env *Enviro
                pos:   pos,
                smap:  smap,
                check: check,
-               env:   check.bestEnv(env),
+               ctxt:  check.bestContext(ctxt),
        }
        return subst.typ(typ)
 }
@@ -65,7 +65,7 @@ type subster struct {
        pos   syntax.Pos
        smap  substMap
        check *Checker // nil if called via Instantiate
-       env   *Environment
+       ctxt  *Context
 }
 
 func (subst *subster) typ(typ Type) Type {
@@ -205,19 +205,19 @@ func (subst *subster) typ(typ Type) Type {
                }
 
                // before creating a new named type, check if we have this one already
-               h := subst.env.TypeHash(t.orig, newTArgs)
+               h := subst.ctxt.TypeHash(t.orig, newTArgs)
                dump(">>> new type hash: %s", h)
-               if named := subst.env.typeForHash(h, nil); named != nil {
+               if named := subst.ctxt.typeForHash(h, nil); named != nil {
                        dump(">>> found %s", named)
                        return named
                }
 
-               // Create a new instance and populate the environment to avoid endless
+               // Create a new instance and populate the context to avoid endless
                // recursion. The position used here is irrelevant because validation only
                // occurs on t (we don't call validType on named), but we use subst.pos to
                // help with debugging.
-               t.orig.resolve(subst.env)
-               return subst.check.instance(subst.pos, t.orig, newTArgs, subst.env)
+               t.orig.resolve(subst.ctxt)
+               return subst.check.instance(subst.pos, t.orig, newTArgs, subst.ctxt)
 
                // Note that if we were to expose substitution more generally (not just in
                // the context of a declaration), we'd have to substitute in
index bdafcf883db9b4b40722bc929889eecbf4cce3d1..930acf053aec6d53bfa39618ccd6f7899c9e9478 100644 (file)
@@ -67,20 +67,20 @@ type typeWriter struct {
        buf  *bytes.Buffer
        seen map[Type]bool
        qf   Qualifier
-       env  *Environment // if non-nil, we are type hashing
+       ctxt *Context // if non-nil, we are type hashing
 }
 
 func newTypeWriter(buf *bytes.Buffer, qf Qualifier) *typeWriter {
        return &typeWriter{buf, make(map[Type]bool), qf, nil}
 }
 
-func newTypeHasher(buf *bytes.Buffer, env *Environment) *typeWriter {
-       assert(env != nil)
-       return &typeWriter{buf, make(map[Type]bool), nil, env}
+func newTypeHasher(buf *bytes.Buffer, ctxt *Context) *typeWriter {
+       assert(ctxt != nil)
+       return &typeWriter{buf, make(map[Type]bool), nil, ctxt}
 }
 
 func (w *typeWriter) byte(b byte) {
-       if w.env != nil {
+       if w.ctxt != nil {
                if b == ' ' {
                        b = '#'
                }
@@ -98,7 +98,7 @@ func (w *typeWriter) string(s string) {
 }
 
 func (w *typeWriter) error(msg string) {
-       if w.env != nil {
+       if w.ctxt != nil {
                panic(msg)
        }
        w.buf.WriteString("<" + msg + ">")
@@ -154,7 +154,7 @@ func (w *typeWriter) typ(typ Type) {
                        if tag := t.Tag(i); tag != "" {
                                w.byte(' ')
                                // TODO(gri) If tag contains blanks, replacing them with '#'
-                               //           in Environment.TypeHash may produce another tag
+                               //           in Context.TypeHash may produce another tag
                                //           accidentally.
                                w.string(strconv.Quote(tag))
                        }
@@ -247,7 +247,7 @@ func (w *typeWriter) typ(typ Type) {
                if t.targs != nil {
                        // instantiated type
                        w.typeList(t.targs.list())
-               } else if w.env == nil && t.TypeParams().Len() != 0 { // For type hashing, don't need to format the TParams
+               } else if w.ctxt == nil && t.TypeParams().Len() != 0 { // For type hashing, don't need to format the TParams
                        // parameterized type
                        w.tParamList(t.TypeParams().list())
                }
@@ -276,12 +276,12 @@ func (w *typeWriter) typ(typ Type) {
        }
 }
 
-// If w.env is non-nil, typePrefix writes a unique prefix for the named type t
-// based on the types already observed by w.env. If w.env is nil, it does
+// If w.ctxt is non-nil, typePrefix writes a unique prefix for the named type t
+// based on the types already observed by w.ctxt. If w.ctxt is nil, it does
 // nothing.
 func (w *typeWriter) typePrefix(t *Named) {
-       if w.env != nil {
-               w.string(strconv.Itoa(w.env.idForType(t)))
+       if w.ctxt != nil {
+               w.string(strconv.Itoa(w.ctxt.idForType(t)))
        }
 }
 
@@ -340,7 +340,7 @@ func (w *typeWriter) tuple(tup *Tuple, variadic bool) {
                                w.byte(',')
                        }
                        // parameter names are ignored for type identity and thus type hashes
-                       if w.env == nil && v.name != "" {
+                       if w.ctxt == nil && v.name != "" {
                                w.string(v.name)
                                w.byte(' ')
                        }
@@ -381,7 +381,7 @@ func (w *typeWriter) signature(sig *Signature) {
        }
 
        w.byte(' ')
-       if n == 1 && (w.env != nil || sig.results.vars[0].name == "") {
+       if n == 1 && (w.ctxt != nil || sig.results.vars[0].name == "") {
                // single unnamed result (if type hashing, name must be ignored)
                w.typ(sig.results.vars[0].typ)
                return
index 0bbd940d074d1d51e55077ef2a2bb40fb8596ad3..c115d07b4182d080df7d7b59263d6cf2c34edca3 100644 (file)
@@ -112,10 +112,9 @@ type ImporterFrom interface {
 // A Config specifies the configuration for type checking.
 // The zero value for Config is a ready-to-use default configuration.
 type Config struct {
-       // Environment is the environment used for resolving global
-       // identifiers. If nil, the type checker will initialize this
-       // field with a newly created environment.
-       Environment *Environment
+       // Context is the context used for resolving global identifiers. If nil, the
+       // type checker will initialize this field with a newly created context.
+       Context *Context
 
        // GoVersion describes the accepted Go language version. The string
        // must follow the format "go%d.%d" (e.g. "go1.12") or it must be
index a55c01c17d43ad86720bc37557f11fdcdd13f6ef..cfcdd68de3de2f512f59f52b28f801642d39916c 100644 (file)
@@ -173,9 +173,9 @@ func NewChecker(conf *Config, fset *token.FileSet, pkg *Package, info *Info) *Ch
                conf = new(Config)
        }
 
-       // make sure we have an environment
-       if conf.Environment == nil {
-               conf.Environment = NewEnvironment()
+       // make sure we have a context
+       if conf.Context == nil {
+               conf.Context = NewContext()
        }
 
        // make sure we have an info struct
similarity index 65%
rename from src/go/types/environment.go
rename to src/go/types/context.go
index b818f8156463b8c9cbf6a67c8a8fdc7b860aaa35..bbdaade6321d0841956cb149b8f279d1b822286f 100644 (file)
@@ -10,21 +10,25 @@ import (
        "sync"
 )
 
-// An Environment is an opaque type checking environment. It may be used to
-// share identical type instances across type-checked packages or calls to
+// An Context is an opaque type checking context. It may be used to share
+// identical type instances across type-checked packages or calls to
 // Instantiate.
 //
 // It is safe for concurrent use.
-type Environment struct {
+type Context struct {
        mu      sync.Mutex
        typeMap map[string]*Named // type hash -> instance
        nextID  int               // next unique ID
        seen    map[*Named]int    // assigned unique IDs
 }
 
-// NewEnvironment creates a new Environment.
-func NewEnvironment() *Environment {
-       return &Environment{
+// Temporary alias to allow x/tools tests to pass.
+// TODO(rfindley): remove the Environment type.
+type Environment = Context
+
+// NewContext creates a new Context.
+func NewContext() *Context {
+       return &Context{
                typeMap: make(map[string]*Named),
                seen:    make(map[*Named]int),
        }
@@ -34,12 +38,12 @@ func NewEnvironment() *Environment {
 // type hash: types that are identical produce identical string representations.
 // If typ is a *Named type and targs is not empty, typ is printed as if it were
 // instantiated with targs. The result is guaranteed to not contain blanks (" ").
-func (env *Environment) typeHash(typ Type, targs []Type) string {
-       assert(env != nil)
+func (ctxt *Context) typeHash(typ Type, targs []Type) string {
+       assert(ctxt != nil)
        assert(typ != nil)
        var buf bytes.Buffer
 
-       h := newTypeHasher(&buf, env)
+       h := newTypeHasher(&buf, ctxt)
        if named, _ := typ.(*Named); named != nil && len(targs) > 0 {
                // Don't use WriteType because we need to use the provided targs
                // and not any targs that might already be with the *Named type.
@@ -56,27 +60,27 @@ func (env *Environment) typeHash(typ Type, targs []Type) string {
 
 // typeForHash returns the recorded type for the type hash h, if it exists.
 // If no type exists for h and n is non-nil, n is recorded for h.
-func (env *Environment) typeForHash(h string, n *Named) *Named {
-       env.mu.Lock()
-       defer env.mu.Unlock()
-       if existing := env.typeMap[h]; existing != nil {
+func (ctxt *Context) typeForHash(h string, n *Named) *Named {
+       ctxt.mu.Lock()
+       defer ctxt.mu.Unlock()
+       if existing := ctxt.typeMap[h]; existing != nil {
                return existing
        }
        if n != nil {
-               env.typeMap[h] = n
+               ctxt.typeMap[h] = n
        }
        return n
 }
 
 // idForType returns a unique ID for the pointer n.
-func (env *Environment) idForType(n *Named) int {
-       env.mu.Lock()
-       defer env.mu.Unlock()
-       id, ok := env.seen[n]
+func (ctxt *Context) idForType(n *Named) int {
+       ctxt.mu.Lock()
+       defer ctxt.mu.Unlock()
+       id, ok := ctxt.seen[n]
        if !ok {
-               id = env.nextID
-               env.seen[n] = id
-               env.nextID++
+               id = ctxt.nextID
+               ctxt.seen[n] = id
+               ctxt.nextID++
        }
        return id
 }
index 77914dd1af97d5b11dd40b9763d0a91661fa3df2..d0809f5a6ee09d83868d5210abf27fbcf702b5ef 100644 (file)
@@ -68,7 +68,7 @@ func (check *Checker) objDecl(obj Object, def *Named) {
        // Funcs with m.instRecv set have not yet be completed. Complete them now
        // so that they have a type when objDecl exits.
        if m, _ := obj.(*Func); m != nil && m.instRecv != nil {
-               check.completeMethod(check.conf.Environment, m)
+               check.completeMethod(check.conf.Context, m)
        }
 
        // Checking the declaration of obj means inferring its type
@@ -329,7 +329,7 @@ func (check *Checker) validType(typ Type, path []Object) typeInfo {
                }
 
        case *Named:
-               t.resolve(check.conf.Environment)
+               t.resolve(check.conf.Context)
                // don't touch the type if it is from a different package or the Universe scope
                // (doing so would lead to a race condition - was issue #35049)
                if t.obj.pkg != check.pkg {
index 6cafc2fbeda609258703830e1399efb359b7b2fe..2a255bcb87e196018b8ea7b004644e1f0526d977 100644 (file)
@@ -20,9 +20,8 @@ import (
 // *Signature). Any methods attached to a *Named are simply copied; they are
 // not instantiated.
 //
-// If env is non-nil, it may be used to de-dupe the instance against previous
-// instances with the same identity. This functionality is currently
-// unimplemented.
+// If ctxt is non-nil, it may be used to de-dupe the instance against previous
+// instances with the same identity.
 //
 // If verify is set and constraint satisfaction fails, the returned error may
 // wrap an *ArgumentError indicating which type argument did not satisfy its
@@ -30,8 +29,8 @@ import (
 //
 // TODO(rfindley): change this function to also return an error if lengths of
 // tparams and targs do not match.
-func Instantiate(env *Environment, typ Type, targs []Type, validate bool) (Type, error) {
-       inst := (*Checker)(nil).instance(token.NoPos, typ, targs, env)
+func Instantiate(ctxt *Context, typ Type, targs []Type, validate bool) (Type, error) {
+       inst := (*Checker)(nil).instance(token.NoPos, typ, targs, ctxt)
 
        var err error
        if validate {
@@ -71,7 +70,7 @@ func (check *Checker) instantiate(pos token.Pos, typ Type, targs []Type, posList
                }()
        }
 
-       inst := check.instance(pos, typ, targs, check.conf.Environment)
+       inst := check.instance(pos, typ, targs, check.conf.Context)
 
        assert(len(posList) <= len(targs))
        check.later(func() {
@@ -103,28 +102,28 @@ func (check *Checker) instantiate(pos token.Pos, typ Type, targs []Type, posList
 // instance creates a type or function instance using the given original type
 // typ and arguments targs. For Named types the resulting instance will be
 // unexpanded.
-func (check *Checker) instance(pos token.Pos, typ Type, targs []Type, env *Environment) Type {
+func (check *Checker) instance(pos token.Pos, typ Type, targs []Type, ctxt *Context) Type {
        switch t := typ.(type) {
        case *Named:
                var h string
-               if env != nil {
-                       h = env.typeHash(t, targs)
+               if ctxt != nil {
+                       h = ctxt.typeHash(t, targs)
                        // typ may already have been instantiated with identical type arguments. In
                        // that case, re-use the existing instance.
-                       if named := env.typeForHash(h, nil); named != nil {
+                       if named := ctxt.typeForHash(h, nil); named != nil {
                                return named
                        }
                }
                tname := NewTypeName(pos, t.obj.pkg, t.obj.name, nil)
                named := check.newNamed(tname, t, nil, nil, nil) // methods and tparams are set when named is resolved
                named.targs = NewTypeList(targs)
-               named.resolver = func(env *Environment, n *Named) (*TypeParamList, Type, []*Func) {
-                       return expandNamed(env, n, pos)
+               named.resolver = func(ctxt *Context, n *Named) (*TypeParamList, Type, []*Func) {
+                       return expandNamed(ctxt, n, pos)
                }
-               if env != nil {
-                       // It's possible that we've lost a race to add named to the environment.
-                       // In this case, use whichever instance is recorded in the environment.
-                       named = env.typeForHash(h, named)
+               if ctxt != nil {
+                       // It's possible that we've lost a race to add named to the context.
+                       // In this case, use whichever instance is recorded in the context.
+                       named = ctxt.typeForHash(h, named)
                }
                return named
 
@@ -136,7 +135,7 @@ func (check *Checker) instance(pos token.Pos, typ Type, targs []Type, env *Envir
                if tparams.Len() == 0 {
                        return typ // nothing to do (minor optimization)
                }
-               sig := check.subst(pos, typ, makeSubstMap(tparams.list(), targs), env).(*Signature)
+               sig := check.subst(pos, typ, makeSubstMap(tparams.list(), targs), ctxt).(*Signature)
                // If the signature doesn't use its type parameters, subst
                // will not make a copy. In that case, make a copy now (so
                // we can set tparams to nil w/o causing side-effects).
@@ -191,7 +190,7 @@ func (check *Checker) satisfies(pos token.Pos, targ Type, tpar *TypeParam, smap
 
        // TODO(rfindley): it would be great if users could pass in a qualifier here,
        // rather than falling back to verbose qualification. Maybe this can be part
-       // of a the shared environment.
+       // of the shared context.
        var qf Qualifier
        if check != nil {
                qf = check.qualifier
index cf6d2a9198688a6de13b020e392f4b734fc953c4..832c8222242504441b225be3304efcc1d5f19c07 100644 (file)
@@ -22,12 +22,12 @@ func TestInstantiateEquality(t *testing.T) {
 
        // Instantiating the same type twice should result in pointer-equivalent
        // instances.
-       env := NewEnvironment()
-       res1, err := Instantiate(env, T, []Type{Typ[Int]}, false)
+       ctxt := NewContext()
+       res1, err := Instantiate(ctxt, T, []Type{Typ[Int]}, false)
        if err != nil {
                t.Fatal(err)
        }
-       res2, err := Instantiate(env, T, []Type{Typ[Int]}, false)
+       res2, err := Instantiate(ctxt, T, []Type{Typ[Int]}, false)
        if err != nil {
                t.Fatal(err)
        }
@@ -50,16 +50,16 @@ func TestInstantiateNonEquality(t *testing.T) {
        }
 
        // We consider T1 and T2 to be distinct types, so their instances should not
-       // be deduplicated by the environment.
+       // be deduplicated by the context.
        T1 := pkg1.Scope().Lookup("T").Type().(*Named)
        T2 := pkg2.Scope().Lookup("T").Type().(*Named)
 
-       env := NewEnvironment()
-       res1, err := Instantiate(env, T1, []Type{Typ[Int]}, false)
+       ctxt := NewContext()
+       res1, err := Instantiate(ctxt, T1, []Type{Typ[Int]}, false)
        if err != nil {
                t.Fatal(err)
        }
-       res2, err := Instantiate(env, T2, []Type{Typ[Int]}, false)
+       res2, err := Instantiate(ctxt, T2, []Type{Typ[Int]}, false)
        if err != nil {
                t.Fatal(err)
        }
index d29c67d4eb3f618f03c2dd0d5a9098d7534e1efc..82b2afcb630ce235ef7d617d8dfffed06d992588 100644 (file)
@@ -22,7 +22,7 @@ type Named struct {
        methods    []*Func        // methods declared for this type (not the method set of this type); signatures are type-checked lazily
 
        // resolver may be provided to lazily resolve type parameters, underlying, and methods.
-       resolver func(*Environment, *Named) (tparams *TypeParamList, underlying Type, methods []*Func)
+       resolver func(*Context, *Named) (tparams *TypeParamList, underlying Type, methods []*Func)
        once     sync.Once // ensures that tparams, underlying, and methods are resolved before accessing
 }
 
@@ -36,7 +36,7 @@ func NewNamed(obj *TypeName, underlying Type, methods []*Func) *Named {
        return (*Checker)(nil).newNamed(obj, nil, underlying, nil, methods)
 }
 
-func (t *Named) resolve(env *Environment) *Named {
+func (t *Named) resolve(ctxt *Context) *Named {
        if t.resolver == nil {
                return t
        }
@@ -50,7 +50,7 @@ func (t *Named) resolve(env *Environment) *Named {
                // methods would need to support reentrant calls though. It would
                // also make the API more future-proof towards further extensions
                // (like SetTypeParams).
-               t.tparams, t.underlying, t.methods = t.resolver(env, t)
+               t.tparams, t.underlying, t.methods = t.resolver(ctxt, t)
                t.fromRHS = t.underlying // for cycle detection
        })
        return t
@@ -219,37 +219,37 @@ func (n *Named) setUnderlying(typ Type) {
        }
 }
 
-// bestEnv returns the best available environment. In order of preference:
-// - the given env, if non-nil
-// - the Checker env, if check is non-nil
-// - a new environment
-func (check *Checker) bestEnv(env *Environment) *Environment {
-       if env != nil {
-               return env
+// bestContext returns the best available context. In order of preference:
+// - the given ctxt, if non-nil
+// - check.Config.Context, if check is non-nil
+// - a new Context
+func (check *Checker) bestContext(ctxt *Context) *Context {
+       if ctxt != nil {
+               return ctxt
        }
        if check != nil {
-               assert(check.conf.Environment != nil)
-               return check.conf.Environment
+               assert(check.conf.Context != nil)
+               return check.conf.Context
        }
-       return NewEnvironment()
+       return NewContext()
 }
 
 // expandNamed ensures that the underlying type of n is instantiated.
 // The underlying type will be Typ[Invalid] if there was an error.
-func expandNamed(env *Environment, n *Named, instPos token.Pos) (tparams *TypeParamList, underlying Type, methods []*Func) {
-       n.orig.resolve(env)
+func expandNamed(ctxt *Context, n *Named, instPos token.Pos) (tparams *TypeParamList, underlying Type, methods []*Func) {
+       n.orig.resolve(ctxt)
 
        check := n.check
 
        if check.validateTArgLen(instPos, n.orig.tparams.Len(), n.targs.Len()) {
-               // We must always have an env, to avoid infinite recursion.
-               env = check.bestEnv(env)
-               h := env.typeHash(n.orig, n.targs.list())
+               // We must always have a context, to avoid infinite recursion.
+               ctxt = check.bestContext(ctxt)
+               h := ctxt.typeHash(n.orig, n.targs.list())
                // ensure that an instance is recorded for h to avoid infinite recursion.
-               env.typeForHash(h, n)
+               ctxt.typeForHash(h, n)
 
                smap := makeSubstMap(n.orig.tparams.list(), n.targs.list())
-               underlying = n.check.subst(instPos, n.orig.underlying, smap, env)
+               underlying = n.check.subst(instPos, n.orig.underlying, smap, ctxt)
 
                for i := 0; i < n.orig.NumMethods(); i++ {
                        origm := n.orig.Method(i)
@@ -274,7 +274,7 @@ func expandNamed(env *Environment, n *Named, instPos token.Pos) (tparams *TypePa
        completeMethods := func() {
                for _, m := range methods {
                        if m.instRecv != nil {
-                               check.completeMethod(env, m)
+                               check.completeMethod(ctxt, m)
                        }
                }
        }
@@ -287,7 +287,7 @@ func expandNamed(env *Environment, n *Named, instPos token.Pos) (tparams *TypePa
        return n.orig.tparams, underlying, methods
 }
 
-func (check *Checker) completeMethod(env *Environment, m *Func) {
+func (check *Checker) completeMethod(ctxt *Context, m *Func) {
        assert(m.instRecv != nil)
        rbase := m.instRecv
        m.instRecv = nil
@@ -308,7 +308,7 @@ func (check *Checker) completeMethod(env *Environment, m *Func) {
        }
 
        smap := makeSubstMap(origSig.RecvTypeParams().list(), rbase.targs.list())
-       sig := check.subst(orig.pos, origSig, smap, env).(*Signature)
+       sig := check.subst(orig.pos, origSig, smap, ctxt).(*Signature)
        if sig == origSig {
                // No substitution occurred, but we still need to create a new signature to
                // hold the instantiated receiver.
index 19e7fddeb6cde2012ad163ab0de6371db9363cc4..18015fc9672d406359925e57ff8724c9599b8535 100644 (file)
@@ -235,7 +235,7 @@ func NewTypeName(pos token.Pos, pkg *Package, name string, typ Type) *TypeName {
 func _NewTypeNameLazy(pos token.Pos, pkg *Package, name string, load func(named *Named) (tparams []*TypeParam, underlying Type, methods []*Func)) *TypeName {
        obj := NewTypeName(pos, pkg, name, nil)
 
-       resolve := func(_ *Environment, t *Named) (*TypeParamList, Type, []*Func) {
+       resolve := func(_ *Context, t *Named) (*TypeParamList, Type, []*Func) {
                tparams, underlying, methods := load(t)
 
                switch underlying.(type) {
index df38e7124b98a137910da90e1db10adec945f556..c26437afe43d72f7b855b9dc9f34ebf0cb0e559d 100644 (file)
@@ -224,7 +224,7 @@ func (check *Checker) funcType(sig *Signature, recvPar *ast.FieldList, ftyp *ast
                        var err string
                        switch T := rtyp.(type) {
                        case *Named:
-                               T.resolve(check.conf.Environment)
+                               T.resolve(check.conf.Context)
                                // The receiver type may be an instantiated type referred to
                                // by an alias (which cannot have receiver parameters for now).
                                if T.TypeArgs() != nil && sig.RecvTypeParams() == nil {
index 25629dca8ac541cc7b294790aae51c6f716e28d1..e539ab54e679ba4793e1267694b1243453c9fc50 100644 (file)
@@ -37,8 +37,8 @@ func (m substMap) lookup(tpar *TypeParam) Type {
 // that it doesn't modify the incoming type. If a substitution took place, the
 // result type is different from the incoming type.
 //
-// If the given environment is non-nil, it is used in lieu of check.env.
-func (check *Checker) subst(pos token.Pos, typ Type, smap substMap, env *Environment) Type {
+// If the given context is non-nil, it is used in lieu of check.Config.Context
+func (check *Checker) subst(pos token.Pos, typ Type, smap substMap, ctxt *Context) Type {
        if smap.empty() {
                return typ
        }
@@ -56,7 +56,7 @@ func (check *Checker) subst(pos token.Pos, typ Type, smap substMap, env *Environ
                pos:   pos,
                smap:  smap,
                check: check,
-               env:   check.bestEnv(env),
+               ctxt:  check.bestContext(ctxt),
        }
        return subst.typ(typ)
 }
@@ -65,7 +65,7 @@ type subster struct {
        pos   token.Pos
        smap  substMap
        check *Checker // nil if called via Instantiate
-       env   *Environment
+       ctxt  *Context
 }
 
 func (subst *subster) typ(typ Type) Type {
@@ -205,19 +205,19 @@ func (subst *subster) typ(typ Type) Type {
                }
 
                // before creating a new named type, check if we have this one already
-               h := subst.env.typeHash(t.orig, newTArgs)
+               h := subst.ctxt.typeHash(t.orig, newTArgs)
                dump(">>> new type hash: %s", h)
-               if named := subst.env.typeForHash(h, nil); named != nil {
+               if named := subst.ctxt.typeForHash(h, nil); named != nil {
                        dump(">>> found %s", named)
                        return named
                }
 
-               // Create a new instance and populate the environment to avoid endless
+               // Create a new instance and populate the context to avoid endless
                // recursion. The position used here is irrelevant because validation only
                // occurs on t (we don't call validType on named), but we use subst.pos to
                // help with debugging.
-               t.orig.resolve(subst.env)
-               return subst.check.instance(subst.pos, t.orig, newTArgs, subst.env)
+               t.orig.resolve(subst.ctxt)
+               return subst.check.instance(subst.pos, t.orig, newTArgs, subst.ctxt)
 
                // Note that if we were to expose substitution more generally (not just in
                // the context of a declaration), we'd have to substitute in
index e5dafc2e0d8f535e585065eda901d9f5dfc5ce21..4a087c4ed17af7994b6ce5c3a91c7bacc3fc9902 100644 (file)
@@ -68,20 +68,20 @@ type typeWriter struct {
        buf  *bytes.Buffer
        seen map[Type]bool
        qf   Qualifier
-       env  *Environment // if non-nil, we are type hashing
+       ctxt *Context // if non-nil, we are type hashing
 }
 
 func newTypeWriter(buf *bytes.Buffer, qf Qualifier) *typeWriter {
        return &typeWriter{buf, make(map[Type]bool), qf, nil}
 }
 
-func newTypeHasher(buf *bytes.Buffer, env *Environment) *typeWriter {
-       assert(env != nil)
-       return &typeWriter{buf, make(map[Type]bool), nil, env}
+func newTypeHasher(buf *bytes.Buffer, ctxt *Context) *typeWriter {
+       assert(ctxt != nil)
+       return &typeWriter{buf, make(map[Type]bool), nil, ctxt}
 }
 
 func (w *typeWriter) byte(b byte) {
-       if w.env != nil {
+       if w.ctxt != nil {
                if b == ' ' {
                        b = '#'
                }
@@ -99,7 +99,7 @@ func (w *typeWriter) string(s string) {
 }
 
 func (w *typeWriter) error(msg string) {
-       if w.env != nil {
+       if w.ctxt != nil {
                panic(msg)
        }
        w.buf.WriteString("<" + msg + ">")
@@ -155,7 +155,7 @@ func (w *typeWriter) typ(typ Type) {
                        if tag := t.Tag(i); tag != "" {
                                w.byte(' ')
                                // TODO(rfindley) If tag contains blanks, replacing them with '#'
-                               //                in Environment.TypeHash may produce another tag
+                               //                in Context.TypeHash may produce another tag
                                //                accidentally.
                                w.string(strconv.Quote(tag))
                        }
@@ -248,7 +248,7 @@ func (w *typeWriter) typ(typ Type) {
                if t.targs != nil {
                        // instantiated type
                        w.typeList(t.targs.list())
-               } else if w.env == nil && t.TypeParams().Len() != 0 { // For type hashing, don't need to format the TypeParams
+               } else if w.ctxt == nil && t.TypeParams().Len() != 0 { // For type hashing, don't need to format the TypeParams
                        // parameterized type
                        w.tParamList(t.TypeParams().list())
                }
@@ -277,12 +277,12 @@ func (w *typeWriter) typ(typ Type) {
        }
 }
 
-// If w.env is non-nil, typePrefix writes a unique prefix for the named type t
-// based on the types already observed by w.env. If w.env is nil, it does
+// If w.ctxt is non-nil, typePrefix writes a unique prefix for the named type t
+// based on the types already observed by w.ctxt. If w.ctxt is nil, it does
 // nothing.
 func (w *typeWriter) typePrefix(t *Named) {
-       if w.env != nil {
-               w.string(strconv.Itoa(w.env.idForType(t)))
+       if w.ctxt != nil {
+               w.string(strconv.Itoa(w.ctxt.idForType(t)))
        }
 }
 
@@ -341,7 +341,7 @@ func (w *typeWriter) tuple(tup *Tuple, variadic bool) {
                                w.byte(',')
                        }
                        // parameter names are ignored for type identity and thus type hashes
-                       if w.env == nil && v.name != "" {
+                       if w.ctxt == nil && v.name != "" {
                                w.string(v.name)
                                w.byte(' ')
                        }
@@ -382,7 +382,7 @@ func (w *typeWriter) signature(sig *Signature) {
        }
 
        w.byte(' ')
-       if n == 1 && (w.env != nil || sig.results.vars[0].name == "") {
+       if n == 1 && (w.ctxt != nil || sig.results.vars[0].name == "") {
                // single unnamed result (if type hashing, name must be ignored)
                w.typ(sig.results.vars[0].typ)
                return