| 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 179 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 190 | 190 |
| 191 ZoneList<Statement*>* body = fun->body(); | 191 ZoneList<Statement*>* body = fun->body(); |
| 192 | 192 |
| 193 // Initialize state. | 193 // Initialize state. |
| 194 ASSERT(scope_ == NULL); | 194 ASSERT(scope_ == NULL); |
| 195 scope_ = fun->scope(); | 195 scope_ = fun->scope(); |
| 196 ASSERT(frame_ == NULL); | 196 ASSERT(frame_ == NULL); |
| 197 VirtualFrame virtual_frame(this); | 197 VirtualFrame virtual_frame(this); |
| 198 frame_ = &virtual_frame; | 198 frame_ = &virtual_frame; |
| 199 cc_reg_ = no_condition; | 199 cc_reg_ = no_condition; |
| 200 |
| 201 // Adjust for function-level loop nesting. |
| 202 loop_nesting_ += fun->loop_nesting(); |
| 203 |
| 200 { | 204 { |
| 201 CodeGenState state(this); | 205 CodeGenState state(this); |
| 202 | 206 |
| 203 // Entry | 207 // Entry |
| 204 // stack: function, receiver, arguments, return address | 208 // stack: function, receiver, arguments, return address |
| 205 // esp: stack pointer | 209 // esp: stack pointer |
| 206 // ebp: frame pointer | 210 // ebp: frame pointer |
| 207 // edi: caller's parameter pointer | 211 // edi: caller's parameter pointer |
| 208 // esi: callee's context | 212 // esi: callee's context |
| 209 | 213 |
| (...skipping 166 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 376 // Generate a return statement if necessary. | 380 // Generate a return statement if necessary. |
| 377 if (body->is_empty() || body->last()->AsReturnStatement() == NULL) { | 381 if (body->is_empty() || body->last()->AsReturnStatement() == NULL) { |
| 378 Literal undefined(Factory::undefined_value()); | 382 Literal undefined(Factory::undefined_value()); |
| 379 ReturnStatement statement(&undefined); | 383 ReturnStatement statement(&undefined); |
| 380 statement.set_statement_pos(fun->end_position()); | 384 statement.set_statement_pos(fun->end_position()); |
| 381 VisitReturnStatement(&statement); | 385 VisitReturnStatement(&statement); |
| 382 } | 386 } |
| 383 } | 387 } |
| 384 } | 388 } |
| 385 | 389 |
| 390 // Adjust for function-level loop nesting. |
| 391 loop_nesting_ -= fun->loop_nesting(); |
| 392 |
| 386 // Code generation state must be reset. | 393 // Code generation state must be reset. |
| 387 scope_ = NULL; | 394 scope_ = NULL; |
| 388 frame_ = NULL; | 395 frame_ = NULL; |
| 389 ASSERT(!has_cc()); | 396 ASSERT(!has_cc()); |
| 390 ASSERT(state_ == NULL); | 397 ASSERT(state_ == NULL); |
| 398 ASSERT(loop_nesting() == 0); |
| 391 } | 399 } |
| 392 | 400 |
| 393 | 401 |
| 394 Operand CodeGenerator::SlotOperand(Slot* slot, Register tmp) { | 402 Operand CodeGenerator::SlotOperand(Slot* slot, Register tmp) { |
| 395 // Currently, this assertion will fail if we try to assign to | 403 // Currently, this assertion will fail if we try to assign to |
| 396 // a constant variable that is constant because it is read-only | 404 // a constant variable that is constant because it is read-only |
| 397 // (such as the variable referring to a named function expression). | 405 // (such as the variable referring to a named function expression). |
| 398 // We need to implement assignments to read-only variables. | 406 // We need to implement assignments to read-only variables. |
| 399 // Ideally, we should do this during AST generation (by converting | 407 // Ideally, we should do this during AST generation (by converting |
| 400 // such assignments into expression statements); however, in general | 408 // such assignments into expression statements); however, in general |
| (...skipping 2286 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2687 // JavaScript example: 'foo(1, 2, 3)' // foo is global | 2695 // JavaScript example: 'foo(1, 2, 3)' // foo is global |
| 2688 // ---------------------------------- | 2696 // ---------------------------------- |
| 2689 | 2697 |
| 2690 // Push the name of the function and the receiver onto the stack. | 2698 // Push the name of the function and the receiver onto the stack. |
| 2691 frame_->Push(Immediate(var->name())); | 2699 frame_->Push(Immediate(var->name())); |
| 2692 | 2700 |
| 2693 // Pass the global object as the receiver and let the IC stub | 2701 // Pass the global object as the receiver and let the IC stub |
| 2694 // patch the stack to use the global proxy as 'this' in the | 2702 // patch the stack to use the global proxy as 'this' in the |
| 2695 // invoked function. | 2703 // invoked function. |
| 2696 LoadGlobal(); | 2704 LoadGlobal(); |
| 2697 | |
| 2698 // Load the arguments. | 2705 // Load the arguments. |
| 2699 for (int i = 0; i < args->length(); i++) { | 2706 for (int i = 0; i < args->length(); i++) { |
| 2700 Load(args->at(i)); | 2707 Load(args->at(i)); |
| 2701 } | 2708 } |
| 2702 | 2709 |
| 2703 // Setup the receiver register and call the IC initialization code. | 2710 // Setup the receiver register and call the IC initialization code. |
| 2704 Handle<Code> stub = ComputeCallInitialize(args->length()); | 2711 Handle<Code> stub = (loop_nesting() > 0) |
| 2712 ? ComputeCallInitializeInLoop(args->length()) |
| 2713 : ComputeCallInitialize(args->length()); |
| 2705 __ RecordPosition(node->position()); | 2714 __ RecordPosition(node->position()); |
| 2706 __ call(stub, RelocInfo::CODE_TARGET_CONTEXT); | 2715 __ call(stub, RelocInfo::CODE_TARGET_CONTEXT); |
| 2707 __ mov(esi, frame_->Context()); | 2716 __ mov(esi, frame_->Context()); |
| 2708 | 2717 |
| 2709 // Overwrite the function on the stack with the result. | 2718 // Overwrite the function on the stack with the result. |
| 2710 __ mov(frame_->Top(), eax); | 2719 __ mov(frame_->Top(), eax); |
| 2711 | 2720 |
| 2712 } else if (var != NULL && var->slot() != NULL && | 2721 } else if (var != NULL && var->slot() != NULL && |
| 2713 var->slot()->type() == Slot::LOOKUP) { | 2722 var->slot()->type() == Slot::LOOKUP) { |
| 2714 // ---------------------------------- | 2723 // ---------------------------------- |
| (...skipping 23 matching lines...) Expand all Loading... |
| 2738 // ------------------------------------------------------------------ | 2747 // ------------------------------------------------------------------ |
| 2739 | 2748 |
| 2740 // Push the name of the function and the receiver onto the stack. | 2749 // Push the name of the function and the receiver onto the stack. |
| 2741 frame_->Push(Immediate(literal->handle())); | 2750 frame_->Push(Immediate(literal->handle())); |
| 2742 Load(property->obj()); | 2751 Load(property->obj()); |
| 2743 | 2752 |
| 2744 // Load the arguments. | 2753 // Load the arguments. |
| 2745 for (int i = 0; i < args->length(); i++) Load(args->at(i)); | 2754 for (int i = 0; i < args->length(); i++) Load(args->at(i)); |
| 2746 | 2755 |
| 2747 // Call the IC initialization code. | 2756 // Call the IC initialization code. |
| 2748 Handle<Code> stub = ComputeCallInitialize(args->length()); | 2757 Handle<Code> stub = (loop_nesting() > 0) |
| 2758 ? ComputeCallInitializeInLoop(args->length()) |
| 2759 : ComputeCallInitialize(args->length()); |
| 2749 __ RecordPosition(node->position()); | 2760 __ RecordPosition(node->position()); |
| 2750 __ call(stub, RelocInfo::CODE_TARGET); | 2761 __ call(stub, RelocInfo::CODE_TARGET); |
| 2751 __ mov(esi, frame_->Context()); | 2762 __ mov(esi, frame_->Context()); |
| 2752 | 2763 |
| 2753 // Overwrite the function on the stack with the result. | 2764 // Overwrite the function on the stack with the result. |
| 2754 __ mov(frame_->Top(), eax); | 2765 __ mov(frame_->Top(), eax); |
| 2755 | 2766 |
| 2756 } else { | 2767 } else { |
| 2757 // ------------------------------------------- | 2768 // ------------------------------------------- |
| 2758 // JavaScript example: 'array[index](1, 2, 3)' | 2769 // JavaScript example: 'array[index](1, 2, 3)' |
| (...skipping 2383 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5142 | 5153 |
| 5143 // Slow-case: Go through the JavaScript implementation. | 5154 // Slow-case: Go through the JavaScript implementation. |
| 5144 __ bind(&slow); | 5155 __ bind(&slow); |
| 5145 __ InvokeBuiltin(Builtins::INSTANCE_OF, JUMP_FUNCTION); | 5156 __ InvokeBuiltin(Builtins::INSTANCE_OF, JUMP_FUNCTION); |
| 5146 } | 5157 } |
| 5147 | 5158 |
| 5148 | 5159 |
| 5149 #undef __ | 5160 #undef __ |
| 5150 | 5161 |
| 5151 } } // namespace v8::internal | 5162 } } // namespace v8::internal |
| OLD | NEW |