示例#1
0
        private void DefineField(ResolutionVisitor resolutionVisitor, INameDeclaration nameDecl)
        {
            if (nameDecl == null)
            {
                // malformed code, for example catch w/o a variable.
                return;
            }
            var field = this[nameDecl.Name];

            if (nameDecl is ParameterDeclaration)
            {
                // function parameters are handled separately, so if this is a parameter declaration,
                // then it must be a catch variable.
                if (field == null)
                {
                    // no collision - create the catch-error field
                    field = new JSVariableField(FieldType.CatchError, nameDecl.Name);

                    this.AddField(field);
                }
                else
                {
                    // it's an error to declare anything in the catch scope with the same name as the
                    // error variable

                    ErrorSink.HandleError(JSError.DuplicateCatch, nameDecl.GetNameSpan(GlobalScope.Node.LocationResolver), resolutionVisitor._locationResolver, true);
                }
            }
            else
            {
                if (field == null)
                {
                    // could be global or local depending on the scope, so let the scope create it.
                    field = this.CreateField(nameDecl.Name);

                    // if this field is a constant, mark it now
                    var lexDeclaration = nameDecl.Parent as LexicalDeclaration;

                    this.AddField(field);
                }
                else
                {
                    // already defined!
                    // if this is a lexical declaration, then it's an error because we have two
                    // lexical declarations with the same name in the same scope.
                    if (nameDecl.Parent is LexicalDeclaration)
                    {
                        _errorSink.HandleError(
                            JSError.DuplicateLexicalDeclaration,
                            nameDecl.GetNameSpan(GlobalScope.Node.LocationResolver),
                            resolutionVisitor._locationResolver,
                            true
                            );
                    }
                }
            }

            nameDecl.VariableField = field;
        }
        private void DefineField(INameDeclaration nameDecl, FunctionObject fieldValue)
        {
            var field = this[nameDecl.Name];
            if (nameDecl is ParameterDeclaration)
            {
                // function parameters are handled separately, so if this is a parameter declaration,
                // then it must be a catch variable. 
                if (field == null)
                {
                    // no collision - create the catch-error field
                    field = new JSVariableField(FieldType.CatchError, nameDecl.Name, 0, null)
                    {
                        OriginalContext = nameDecl.NameContext.Clone(),
                        IsDeclared = true
                    };

                    this.AddField(field);
                }
                else
                {
                    // it's an error to declare anything in the catch scope with the same name as the
                    // error variable
                    field.OriginalContext.HandleError(JSError.DuplicateCatch, true);
                }
            }
            else
            {
                if (field == null)
                {
                    // could be global or local depending on the scope, so let the scope create it.
                    field = this.CreateField(nameDecl.Name, null, 0);
                    field.OriginalContext = nameDecl.NameContext.Clone();
                    field.IsDeclared = true;
                    field.IsFunction = (nameDecl is FunctionObject);
                    field.FieldValue = fieldValue;

                    // if this field is a constant, mark it now
                    var lexDeclaration = nameDecl.Parent as LexicalDeclaration;
                    field.InitializationOnly = nameDecl.Parent is ConstStatement
                        || (lexDeclaration != null && lexDeclaration.StatementToken == JSToken.Const);

                    this.AddField(field);
                }
                else
                {
                    // already defined! 
                    // if this is a lexical declaration, then it's an error because we have two
                    // lexical declarations with the same name in the same scope.
                    if (nameDecl.Parent is LexicalDeclaration)
                    {
                        nameDecl.NameContext.HandleError(JSError.DuplicateLexicalDeclaration, true);
                    }

                    if (nameDecl.Initializer != null)
                    {
                        // if this is an initialized declaration, then the var part is
                        // superfluous and the "initializer" is really a lookup assignment. 
                        // So bump up the ref-count for those cases.
                        var nameReference = nameDecl as INameReference;
                        if (nameReference != null)
                        {
                            field.AddReference(nameReference);
                        }
                    }

                    // don't clobber an existing field value with null. For instance, the last 
                    // function declaration is the winner, so always set the value if we have something,
                    // but a var following a function shouldn't reset it to null.
                    if (fieldValue != null)
                    {
                        field.FieldValue = fieldValue;
                    }
                }
            }

            nameDecl.VariableField = field;
            field.Declarations.Add(nameDecl);

            // if this scope is within a with-statement, or if the declaration was flagged
            // as not being renamable, then mark the field as not crunchable
            if (IsInWithScope || nameDecl.RenameNotAllowed)
            {
                field.CanCrunch = false;
            }
        }
        private void DefineField(INameDeclaration nameDecl, FunctionObject fieldValue)
        {
            var field = this[nameDecl.Name];

            if (nameDecl is ParameterDeclaration)
            {
                // function parameters are handled separately, so if this is a parameter declaration,
                // then it must be a catch variable.
                if (field == null)
                {
                    // no collision - create the catch-error field
                    field = new JSVariableField(FieldType.CatchError, nameDecl.Name, 0, null)
                    {
                        OriginalContext = nameDecl.NameContext.Clone(),
                        IsDeclared      = true
                    };

                    this.AddField(field);
                }
                else
                {
                    // it's an error to declare anything in the catch scope with the same name as the
                    // error variable
                    field.OriginalContext.HandleError(JSError.DuplicateCatch, true);
                }
            }
            else
            {
                if (field == null)
                {
                    // could be global or local depending on the scope, so let the scope create it.
                    field = this.CreateField(nameDecl.Name, null, 0);
                    field.OriginalContext = nameDecl.NameContext.Clone();
                    field.IsDeclared      = true;
                    field.IsFunction      = (nameDecl is FunctionObject);
                    field.FieldValue      = fieldValue;

                    // if this field is a constant, mark it now
                    var lexDeclaration = nameDecl.Parent as LexicalDeclaration;
                    field.InitializationOnly = nameDecl.Parent is ConstStatement ||
                                               (lexDeclaration != null && lexDeclaration.StatementToken == JSToken.Const);

                    this.AddField(field);
                }
                else
                {
                    // already defined!
                    // if this is a lexical declaration, then it's an error because we have two
                    // lexical declarations with the same name in the same scope.
                    if (nameDecl.Parent is LexicalDeclaration)
                    {
                        nameDecl.NameContext.HandleError(JSError.DuplicateLexicalDeclaration, true);
                    }

                    if (nameDecl.Initializer != null)
                    {
                        // if this is an initialized declaration, then the var part is
                        // superfluous and the "initializer" is really a lookup assignment.
                        // So bump up the ref-count for those cases.
                        var nameReference = nameDecl as INameReference;
                        if (nameReference != null)
                        {
                            field.AddReference(nameReference);
                        }
                    }

                    // don't clobber an existing field value with null. For instance, the last
                    // function declaration is the winner, so always set the value if we have something,
                    // but a var following a function shouldn't reset it to null.
                    if (fieldValue != null)
                    {
                        field.FieldValue = fieldValue;
                    }
                }
            }

            nameDecl.VariableField = field;
            field.Declarations.Add(nameDecl);

            // if this scope is within a with-statement, or if the declaration was flagged
            // as not being renamable, then mark the field as not crunchable
            if (IsInWithScope || nameDecl.RenameNotAllowed)
            {
                field.CanCrunch = false;
            }
        }
        private void DefineField(ResolutionVisitor resolutionVisitor, INameDeclaration nameDecl)
        {
            if (nameDecl == null) {
                // malformed code, for example catch w/o a variable.
                return;
            }
            var field = this[nameDecl.Name];
            if (nameDecl is ParameterDeclaration)
            {
                // function parameters are handled separately, so if this is a parameter declaration,
                // then it must be a catch variable. 
                if (field == null)
                {
                    // no collision - create the catch-error field
                    field = new JSVariableField(FieldType.CatchError, nameDecl.Name);

                    this.AddField(field);
                }
                else
                {
                    // it's an error to declare anything in the catch scope with the same name as the
                    // error variable
                    
                    ErrorSink.HandleError(JSError.DuplicateCatch, nameDecl.GetNameSpan(GlobalScope.Node.LocationResolver), resolutionVisitor._locationResolver, true);
                }
            }
            else
            {
                if (field == null)
                {
                    // could be global or local depending on the scope, so let the scope create it.
                    field = this.CreateField(nameDecl.Name);
                    
                    // if this field is a constant, mark it now
                    var lexDeclaration = nameDecl.Parent as LexicalDeclaration;

                    this.AddField(field);
                }
                else
                {
                    // already defined! 
                    // if this is a lexical declaration, then it's an error because we have two
                    // lexical declarations with the same name in the same scope.
                    if (nameDecl.Parent is LexicalDeclaration)
                    {
                        _errorSink.HandleError(
                            JSError.DuplicateLexicalDeclaration, 
                            nameDecl.GetNameSpan(GlobalScope.Node.LocationResolver), 
                            resolutionVisitor._locationResolver, 
                            true
                        );
                    }
                }
            }

            nameDecl.VariableField = field;
        }