| OLD | NEW |
| 1 // Copyright 2006-2009 the V8 project authors. All rights reserved. | 1 // Copyright 2006-2009 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 727 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 738 // Handle load cache miss. | 738 // Handle load cache miss. |
| 739 __ bind(&miss); | 739 __ bind(&miss); |
| 740 Handle<Code> ic = ComputeCallMiss(argc); | 740 Handle<Code> ic = ComputeCallMiss(argc); |
| 741 __ jmp(ic, RelocInfo::CODE_TARGET); | 741 __ jmp(ic, RelocInfo::CODE_TARGET); |
| 742 | 742 |
| 743 // Return the generated code. | 743 // Return the generated code. |
| 744 return GetCode(INTERCEPTOR, name); | 744 return GetCode(INTERCEPTOR, name); |
| 745 } | 745 } |
| 746 | 746 |
| 747 | 747 |
| 748 Object* CallStubCompiler::CompileCallGlobal(GlobalObject* object, | 748 Object* CallStubCompiler::CompileCallGlobal(JSObject* object, |
| 749 GlobalObject* holder, |
| 749 JSGlobalPropertyCell* cell, | 750 JSGlobalPropertyCell* cell, |
| 750 JSFunction* function, | 751 JSFunction* function, |
| 751 String* name) { | 752 String* name) { |
| 752 // ----------- S t a t e ------------- | 753 // ----------- S t a t e ------------- |
| 753 // ----------------------------------- | 754 // ----------------------------------- |
| 754 Label miss; | 755 Label miss; |
| 755 | 756 |
| 756 __ IncrementCounter(&Counters::call_global_inline, 1); | 757 __ IncrementCounter(&Counters::call_global_inline, 1); |
| 757 | 758 |
| 758 // Get the number of arguments. | 759 // Get the number of arguments. |
| 759 const int argc = arguments().immediate(); | 760 const int argc = arguments().immediate(); |
| 760 | 761 |
| 761 // Check that the map of the global has not changed. | 762 // Get the receiver from the stack. |
| 762 __ mov(edx, Operand(esp, (argc + 1) * kPointerSize)); | 763 __ mov(edx, Operand(esp, (argc + 1) * kPointerSize)); |
| 763 __ cmp(FieldOperand(edx, HeapObject::kMapOffset), | 764 |
| 764 Immediate(Handle<Map>(object->map()))); | 765 // If the object is the holder then we know that it's a global |
| 765 __ j(not_equal, &miss, not_taken); | 766 // object which can only happen for contextual calls. In this case, |
| 767 // the receiver cannot be a smi. |
| 768 if (object != holder) { |
| 769 __ test(edx, Immediate(kSmiTagMask)); |
| 770 __ j(zero, &miss, not_taken); |
| 771 } |
| 772 |
| 773 // Check that the maps haven't changed. |
| 774 masm()->CheckMaps(object, edx, holder, ebx, ecx, &miss); |
| 766 | 775 |
| 767 // Get the value from the cell. | 776 // Get the value from the cell. |
| 768 __ mov(edi, Immediate(Handle<JSGlobalPropertyCell>(cell))); | 777 __ mov(edi, Immediate(Handle<JSGlobalPropertyCell>(cell))); |
| 769 __ mov(edi, FieldOperand(edi, JSGlobalPropertyCell::kValueOffset)); | 778 __ mov(edi, FieldOperand(edi, JSGlobalPropertyCell::kValueOffset)); |
| 770 | 779 |
| 771 // Check that the cell contains the same function. | 780 // Check that the cell contains the same function. |
| 772 __ cmp(Operand(edi), Immediate(Handle<JSFunction>(function))); | 781 __ cmp(Operand(edi), Immediate(Handle<JSFunction>(function))); |
| 773 __ j(not_equal, &miss, not_taken); | 782 __ j(not_equal, &miss, not_taken); |
| 774 | 783 |
| 775 // Patch the receiver on the stack with the global proxy. | 784 // Patch the receiver on the stack with the global proxy. |
| 776 __ mov(edx, FieldOperand(edx, GlobalObject::kGlobalReceiverOffset)); | 785 if (object->IsGlobalObject()) { |
| 777 __ mov(Operand(esp, (argc + 1) * kPointerSize), edx); | 786 __ mov(edx, FieldOperand(edx, GlobalObject::kGlobalReceiverOffset)); |
| 787 __ mov(Operand(esp, (argc + 1) * kPointerSize), edx); |
| 788 } |
| 778 | 789 |
| 779 // Setup the context (function already in edi). | 790 // Setup the context (function already in edi). |
| 780 __ mov(esi, FieldOperand(edi, JSFunction::kContextOffset)); | 791 __ mov(esi, FieldOperand(edi, JSFunction::kContextOffset)); |
| 781 | 792 |
| 782 // Jump to the cached code (tail call). | 793 // Jump to the cached code (tail call). |
| 783 ASSERT(function->is_compiled()); | 794 ASSERT(function->is_compiled()); |
| 784 Handle<Code> code(function->code()); | 795 Handle<Code> code(function->code()); |
| 785 ParameterCount expected(function->shared()->formal_parameter_count()); | 796 ParameterCount expected(function->shared()->formal_parameter_count()); |
| 786 __ InvokeCode(code, expected, arguments(), | 797 __ InvokeCode(code, expected, arguments(), |
| 787 RelocInfo::CODE_TARGET, JUMP_FUNCTION); | 798 RelocInfo::CODE_TARGET, JUMP_FUNCTION); |
| (...skipping 327 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1115 &miss); | 1126 &miss); |
| 1116 | 1127 |
| 1117 __ bind(&miss); | 1128 __ bind(&miss); |
| 1118 GenerateLoadMiss(masm(), Code::LOAD_IC); | 1129 GenerateLoadMiss(masm(), Code::LOAD_IC); |
| 1119 | 1130 |
| 1120 // Return the generated code. | 1131 // Return the generated code. |
| 1121 return GetCode(INTERCEPTOR, name); | 1132 return GetCode(INTERCEPTOR, name); |
| 1122 } | 1133 } |
| 1123 | 1134 |
| 1124 | 1135 |
| 1125 Object* LoadStubCompiler::CompileLoadGlobal(GlobalObject* object, | 1136 Object* LoadStubCompiler::CompileLoadGlobal(JSObject* object, |
| 1137 GlobalObject* holder, |
| 1126 JSGlobalPropertyCell* cell, | 1138 JSGlobalPropertyCell* cell, |
| 1127 String* name, | 1139 String* name, |
| 1128 bool is_dont_delete) { | 1140 bool is_dont_delete) { |
| 1129 // ----------- S t a t e ------------- | 1141 // ----------- S t a t e ------------- |
| 1130 // -- ecx : name | 1142 // -- ecx : name |
| 1131 // -- esp[0] : return address | 1143 // -- esp[0] : return address |
| 1132 // -- esp[4] : receiver | 1144 // -- esp[4] : receiver |
| 1133 // ----------------------------------- | 1145 // ----------------------------------- |
| 1134 Label miss; | 1146 Label miss; |
| 1135 | 1147 |
| 1136 __ IncrementCounter(&Counters::named_load_global_inline, 1); | 1148 __ IncrementCounter(&Counters::named_load_global_inline, 1); |
| 1137 | 1149 |
| 1138 // Check that the map of the global has not changed. | 1150 // Get the receiver from the stack. |
| 1139 __ mov(eax, (Operand(esp, kPointerSize))); | 1151 __ mov(eax, (Operand(esp, kPointerSize))); |
| 1140 __ cmp(FieldOperand(eax, HeapObject::kMapOffset), | 1152 |
| 1141 Immediate(Handle<Map>(object->map()))); | 1153 // If the object is the holder then we know that it's a global |
| 1142 __ j(not_equal, &miss, not_taken); | 1154 // object which can only happen for contextual loads. In this case, |
| 1155 // the receiver cannot be a smi. |
| 1156 if (object != holder) { |
| 1157 __ test(eax, Immediate(kSmiTagMask)); |
| 1158 __ j(zero, &miss, not_taken); |
| 1159 } |
| 1160 |
| 1161 // Check that the maps haven't changed. |
| 1162 masm()->CheckMaps(object, eax, holder, ebx, edx, &miss); |
| 1143 | 1163 |
| 1144 // Get the value from the cell. | 1164 // Get the value from the cell. |
| 1145 __ mov(eax, Immediate(Handle<JSGlobalPropertyCell>(cell))); | 1165 __ mov(eax, Immediate(Handle<JSGlobalPropertyCell>(cell))); |
| 1146 __ mov(eax, FieldOperand(eax, JSGlobalPropertyCell::kValueOffset)); | 1166 __ mov(eax, FieldOperand(eax, JSGlobalPropertyCell::kValueOffset)); |
| 1147 | 1167 |
| 1148 // Check for deleted property if property can actually be deleted. | 1168 // Check for deleted property if property can actually be deleted. |
| 1149 if (!is_dont_delete) { | 1169 if (!is_dont_delete) { |
| 1150 __ cmp(eax, Factory::the_hole_value()); | 1170 __ cmp(eax, Factory::the_hole_value()); |
| 1151 __ j(equal, &miss, not_taken); | 1171 __ j(equal, &miss, not_taken); |
| 1152 } else if (FLAG_debug_code) { | 1172 } else if (FLAG_debug_code) { |
| (...skipping 213 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1366 GenerateLoadMiss(masm(), Code::KEYED_LOAD_IC); | 1386 GenerateLoadMiss(masm(), Code::KEYED_LOAD_IC); |
| 1367 | 1387 |
| 1368 // Return the generated code. | 1388 // Return the generated code. |
| 1369 return GetCode(CALLBACKS, name); | 1389 return GetCode(CALLBACKS, name); |
| 1370 } | 1390 } |
| 1371 | 1391 |
| 1372 | 1392 |
| 1373 #undef __ | 1393 #undef __ |
| 1374 | 1394 |
| 1375 } } // namespace v8::internal | 1395 } } // namespace v8::internal |
| OLD | NEW |