OLD | NEW |
1 // Copyright 2006-2008 the V8 project authors. All rights reserved. | 1 // Copyright 2006-2008 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 3793 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3804 __ push(ebx); | 3804 __ push(ebx); |
3805 } | 3805 } |
3806 | 3806 |
3807 | 3807 |
3808 // This deferred code stub will be used for creating the boilerplate | 3808 // This deferred code stub will be used for creating the boilerplate |
3809 // by calling Runtime_CreateObjectLiteral. | 3809 // by calling Runtime_CreateObjectLiteral. |
3810 // Each created boilerplate is stored in the JSFunction and they are | 3810 // Each created boilerplate is stored in the JSFunction and they are |
3811 // therefore context dependent. | 3811 // therefore context dependent. |
3812 class ObjectLiteralDeferred: public DeferredCode { | 3812 class ObjectLiteralDeferred: public DeferredCode { |
3813 public: | 3813 public: |
3814 ObjectLiteralDeferred(CodeGenerator* generator, ObjectLiteral* node) | 3814 ObjectLiteralDeferred(CodeGenerator* generator, |
| 3815 ObjectLiteral* node) |
3815 : DeferredCode(generator), node_(node) { | 3816 : DeferredCode(generator), node_(node) { |
3816 set_comment("[ ObjectLiteralDeferred"); | 3817 set_comment("[ ObjectLiteralDeferred"); |
3817 } | 3818 } |
3818 virtual void Generate(); | 3819 virtual void Generate(); |
3819 private: | 3820 private: |
3820 ObjectLiteral* node_; | 3821 ObjectLiteral* node_; |
3821 }; | 3822 }; |
3822 | 3823 |
3823 | 3824 |
3824 void ObjectLiteralDeferred::Generate() { | 3825 void ObjectLiteralDeferred::Generate() { |
3825 // If the entry is undefined we call the runtime system to compute | 3826 // If the entry is undefined we call the runtime system to compute |
3826 // the literal. | 3827 // the literal. |
3827 | 3828 |
3828 // Literal array (0). | 3829 // Literal array (0). |
3829 __ push(Operand(ecx)); | 3830 __ push(Operand(ecx)); |
3830 // Literal index (1). | 3831 // Literal index (1). |
3831 __ push(Immediate(Smi::FromInt(node_->literal_index()))); | 3832 __ push(Immediate(Smi::FromInt(node_->literal_index()))); |
3832 // Constant properties (2). | 3833 // Constant properties (2). |
3833 __ push(Immediate(node_->constant_properties())); | 3834 __ push(Immediate(node_->constant_properties())); |
3834 __ CallRuntime(Runtime::kCreateObjectLiteralBoilerplate, 3); | 3835 __ CallRuntime(Runtime::kCreateObjectLiteralBoilerplate, 3); |
3835 __ mov(ebx, Operand(eax)); | 3836 __ mov(ebx, Operand(eax)); |
3836 } | 3837 } |
3837 | 3838 |
3838 | 3839 |
3839 void Ia32CodeGenerator::VisitObjectLiteral(ObjectLiteral* node) { | 3840 void Ia32CodeGenerator::VisitObjectLiteral(ObjectLiteral* node) { |
3840 Comment cmnt(masm_, "[ ObjectLiteral"); | 3841 Comment cmnt(masm_, "[ ObjectLiteral"); |
3841 | |
3842 ObjectLiteralDeferred* deferred = new ObjectLiteralDeferred(this, node); | 3842 ObjectLiteralDeferred* deferred = new ObjectLiteralDeferred(this, node); |
3843 | 3843 |
3844 // Retrieve the literal array and check the allocated entry. | 3844 // Retrieve the literal array and check the allocated entry. |
3845 | 3845 |
3846 // Load the function of this activation. | 3846 // Load the function of this activation. |
3847 __ mov(ecx, FunctionOperand()); | 3847 __ mov(ecx, FunctionOperand()); |
3848 | 3848 |
3849 // Load the literals array of the function. | 3849 // Load the literals array of the function. |
3850 __ mov(ecx, FieldOperand(ecx, JSFunction::kLiteralsOffset)); | 3850 __ mov(ecx, FieldOperand(ecx, JSFunction::kLiteralsOffset)); |
3851 | 3851 |
3852 // Load the literal at the ast saved index. | 3852 // Load the literal at the ast saved index. |
3853 int literal_offset = | 3853 int literal_offset = |
3854 FixedArray::kHeaderSize + node->literal_index() * kPointerSize; | 3854 FixedArray::kHeaderSize + node->literal_index() * kPointerSize; |
3855 __ mov(ebx, FieldOperand(ecx, literal_offset)); | 3855 __ mov(ebx, FieldOperand(ecx, literal_offset)); |
3856 | 3856 |
3857 // Check whether we need to materialize the object literal boilerplate. | 3857 // Check whether we need to materialize the object literal boilerplate. |
3858 // If so, jump to the deferred code. | 3858 // If so, jump to the deferred code. |
3859 __ cmp(ebx, Factory::undefined_value()); | 3859 __ cmp(ebx, Factory::undefined_value()); |
3860 __ j(equal, deferred->enter(), not_taken); | 3860 __ j(equal, deferred->enter(), not_taken); |
3861 __ bind(deferred->exit()); | 3861 __ bind(deferred->exit()); |
3862 | 3862 |
3863 // Push the literal. | 3863 // Push the literal. |
3864 __ push(ebx); | 3864 __ push(ebx); |
3865 // Clone the boilerplate object. | 3865 // Clone the boilerplate object. |
3866 __ CallRuntime(Runtime::kCloneObjectLiteralBoilerplate, 1); | 3866 __ CallRuntime(Runtime::kCloneObjectLiteralBoilerplate, 1); |
3867 // Push the new cloned literal object as the result. | 3867 // Push the new cloned literal object as the result. |
3868 __ push(eax); | 3868 __ push(eax); |
3869 | 3869 |
| 3870 |
3870 for (int i = 0; i < node->properties()->length(); i++) { | 3871 for (int i = 0; i < node->properties()->length(); i++) { |
3871 ObjectLiteral::Property* property = node->properties()->at(i); | 3872 ObjectLiteral::Property* property = node->properties()->at(i); |
3872 switch (property->kind()) { | 3873 switch (property->kind()) { |
3873 case ObjectLiteral::Property::CONSTANT: break; | 3874 case ObjectLiteral::Property::CONSTANT: break; |
3874 case ObjectLiteral::Property::COMPUTED: { | 3875 case ObjectLiteral::Property::COMPUTED: { |
3875 Handle<Object> key(property->key()->handle()); | 3876 Handle<Object> key(property->key()->handle()); |
3876 Handle<Code> ic(Builtins::builtin(Builtins::StoreIC_Initialize)); | 3877 Handle<Code> ic(Builtins::builtin(Builtins::StoreIC_Initialize)); |
3877 if (key->IsSymbol()) { | 3878 if (key->IsSymbol()) { |
3878 __ mov(eax, TOS); | 3879 __ mov(eax, TOS); |
3879 __ push(eax); | 3880 __ push(eax); |
(...skipping 1609 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5489 bool is_eval) { | 5490 bool is_eval) { |
5490 Handle<Code> code = Ia32CodeGenerator::MakeCode(fun, script, is_eval); | 5491 Handle<Code> code = Ia32CodeGenerator::MakeCode(fun, script, is_eval); |
5491 if (!code.is_null()) { | 5492 if (!code.is_null()) { |
5492 Counters::total_compiled_code_size.Increment(code->instruction_size()); | 5493 Counters::total_compiled_code_size.Increment(code->instruction_size()); |
5493 } | 5494 } |
5494 return code; | 5495 return code; |
5495 } | 5496 } |
5496 | 5497 |
5497 | 5498 |
5498 } } // namespace v8::internal | 5499 } } // namespace v8::internal |
OLD | NEW |