function getSymbolScope(symbol) {
                // If this is the symbol of a named function expression or named class expression,
                // then named references are limited to its own scope.
                var valueDeclaration = symbol.valueDeclaration;
                if (valueDeclaration && (valueDeclaration.kind === 173 /* FunctionExpression */ || valueDeclaration.kind === 186 /* ClassExpression */)) {
                    return valueDeclaration;
                }
                // If this is private property or method, the scope is the containing class
                if (symbol.flags & (4 /* Property */ | 8192 /* Method */)) {
                    var privateDeclaration = ts.forEach(symbol.getDeclarations(), function (d) { return (d.flags & 16 /* Private */) ? d : undefined; });
                    if (privateDeclaration) {
                        return ts.getAncestor(privateDeclaration, 214 /* ClassDeclaration */);
                    }
                }
                // If the symbol is an import we would like to find it if we are looking for what it imports.
                // So consider it visibile outside its declaration scope.
                if (symbol.flags & 8388608 /* Alias */) {
                    return undefined;
                }
                // if this symbol is visible from its parent container, e.g. exported, then bail out
                // if symbol correspond to the union property - bail out
                if (symbol.parent || (symbol.flags & 268435456 /* SyntheticProperty */)) {
                    return undefined;
                }
                var scope = undefined;
                var declarations = symbol.getDeclarations();
                if (declarations) {
                    for (var _i = 0, declarations_8 = declarations; _i < declarations_8.length; _i++) {
                        var declaration = declarations_8[_i];
                        var container = getContainerNode(declaration);
                        if (!container) {
                            return undefined;
                        }
                        if (scope && scope !== container) {
                            // Different declarations have different containers, bail out
                            return undefined;
                        }
                        if (container.kind === 248 /* SourceFile */ && !ts.isExternalModule(container)) {
                            // This is a global variable and not an external module, any declaration defined
                            // within this scope is visible outside the file
                            return undefined;
                        }
                        // The search scope is the container node
                        scope = container;
                    }
                }
                return scope;
            }
Determines the smallest scope in which a symbol may have named references.
Note that not every construct has been accounted for. This function can
probably be improved.

@returns undefined if the scope cannot be determined, implying that
a reference to a symbol can occur anywhere.