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 68 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
79 __ jmp(Handle<Code>(builtin(ArgumentsAdaptorTrampoline)), | 79 __ jmp(Handle<Code>(builtin(ArgumentsAdaptorTrampoline)), |
80 RelocInfo::CODE_TARGET); | 80 RelocInfo::CODE_TARGET); |
81 } | 81 } |
82 | 82 |
83 | 83 |
84 void Builtins::Generate_JSConstructStubGeneric(MacroAssembler* masm) { | 84 void Builtins::Generate_JSConstructStubGeneric(MacroAssembler* masm) { |
85 // Enter a construct frame. | 85 // Enter a construct frame. |
86 __ EnterConstructFrame(); | 86 __ EnterConstructFrame(); |
87 | 87 |
88 // Store a smi-tagged arguments count on the stack. | 88 // Store a smi-tagged arguments count on the stack. |
89 __ shl(eax, kSmiTagSize); | 89 __ SmiTag(eax); |
90 __ push(eax); | 90 __ push(eax); |
91 | 91 |
92 // Push the function to invoke on the stack. | 92 // Push the function to invoke on the stack. |
93 __ push(edi); | 93 __ push(edi); |
94 | 94 |
95 // Try to allocate the object without transitioning into C code. If any of the | 95 // Try to allocate the object without transitioning into C code. If any of the |
96 // preconditions is not met, the code bails out to the runtime call. | 96 // preconditions is not met, the code bails out to the runtime call. |
97 Label rt_call, allocated; | 97 Label rt_call, allocated; |
98 if (FLAG_inline_new) { | 98 if (FLAG_inline_new) { |
99 Label undo_allocation; | 99 Label undo_allocation; |
(...skipping 148 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
248 __ mov(ebx, Operand(eax)); // store result in ebx | 248 __ mov(ebx, Operand(eax)); // store result in ebx |
249 | 249 |
250 // New object allocated. | 250 // New object allocated. |
251 // ebx: newly allocated object | 251 // ebx: newly allocated object |
252 __ bind(&allocated); | 252 __ bind(&allocated); |
253 // Retrieve the function from the stack. | 253 // Retrieve the function from the stack. |
254 __ pop(edi); | 254 __ pop(edi); |
255 | 255 |
256 // Retrieve smi-tagged arguments count from the stack. | 256 // Retrieve smi-tagged arguments count from the stack. |
257 __ mov(eax, Operand(esp, 0)); | 257 __ mov(eax, Operand(esp, 0)); |
258 __ shr(eax, kSmiTagSize); | 258 __ SmiUntag(eax); |
259 | 259 |
260 // Push the allocated receiver to the stack. We need two copies | 260 // Push the allocated receiver to the stack. We need two copies |
261 // because we may have to return the original one and the calling | 261 // because we may have to return the original one and the calling |
262 // conventions dictate that the called function pops the receiver. | 262 // conventions dictate that the called function pops the receiver. |
263 __ push(ebx); | 263 __ push(ebx); |
264 __ push(ebx); | 264 __ push(ebx); |
265 | 265 |
266 // Setup pointer to last argument. | 266 // Setup pointer to last argument. |
267 __ lea(ebx, Operand(ebp, StandardFrameConstants::kCallerSPOffset)); | 267 __ lea(ebx, Operand(ebp, StandardFrameConstants::kCallerSPOffset)); |
268 | 268 |
(...skipping 164 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
433 __ movzx_b(ecx, FieldOperand(ecx, Map::kInstanceTypeOffset)); | 433 __ movzx_b(ecx, FieldOperand(ecx, Map::kInstanceTypeOffset)); |
434 __ cmp(ecx, FIRST_JS_OBJECT_TYPE); | 434 __ cmp(ecx, FIRST_JS_OBJECT_TYPE); |
435 __ j(less, &call_to_object); | 435 __ j(less, &call_to_object); |
436 __ cmp(ecx, LAST_JS_OBJECT_TYPE); | 436 __ cmp(ecx, LAST_JS_OBJECT_TYPE); |
437 __ j(less_equal, &done); | 437 __ j(less_equal, &done); |
438 | 438 |
439 __ bind(&call_to_object); | 439 __ bind(&call_to_object); |
440 __ EnterInternalFrame(); // preserves eax, ebx, edi | 440 __ EnterInternalFrame(); // preserves eax, ebx, edi |
441 | 441 |
442 // Store the arguments count on the stack (smi tagged). | 442 // Store the arguments count on the stack (smi tagged). |
443 ASSERT(kSmiTag == 0); | 443 __ SmiTag(eax); |
444 __ shl(eax, kSmiTagSize); | |
445 __ push(eax); | 444 __ push(eax); |
446 | 445 |
447 __ push(edi); // save edi across the call | 446 __ push(edi); // save edi across the call |
448 __ push(ebx); | 447 __ push(ebx); |
449 __ InvokeBuiltin(Builtins::TO_OBJECT, CALL_FUNCTION); | 448 __ InvokeBuiltin(Builtins::TO_OBJECT, CALL_FUNCTION); |
450 __ mov(ebx, eax); | 449 __ mov(ebx, eax); |
451 __ pop(edi); // restore edi after the call | 450 __ pop(edi); // restore edi after the call |
452 | 451 |
453 // Get the arguments count and untag it. | 452 // Get the arguments count and untag it. |
454 __ pop(eax); | 453 __ pop(eax); |
455 __ shr(eax, kSmiTagSize); | 454 __ SmiUntag(eax); |
456 | 455 |
457 __ LeaveInternalFrame(); | 456 __ LeaveInternalFrame(); |
458 __ jmp(&patch_receiver); | 457 __ jmp(&patch_receiver); |
459 | 458 |
460 // Use the global receiver object from the called function as the receiver. | 459 // Use the global receiver object from the called function as the receiver. |
461 __ bind(&use_global_receiver); | 460 __ bind(&use_global_receiver); |
462 const int kGlobalIndex = | 461 const int kGlobalIndex = |
463 Context::kHeaderSize + Context::GLOBAL_INDEX * kPointerSize; | 462 Context::kHeaderSize + Context::GLOBAL_INDEX * kPointerSize; |
464 __ mov(ebx, FieldOperand(esi, kGlobalIndex)); | 463 __ mov(ebx, FieldOperand(esi, kGlobalIndex)); |
465 __ mov(ebx, FieldOperand(ebx, GlobalObject::kGlobalContextOffset)); | 464 __ mov(ebx, FieldOperand(ebx, GlobalObject::kGlobalContextOffset)); |
(...skipping 161 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
627 __ mov(eax, Operand(ebp, kIndexOffset)); | 626 __ mov(eax, Operand(ebp, kIndexOffset)); |
628 __ add(Operand(eax), Immediate(1 << kSmiTagSize)); | 627 __ add(Operand(eax), Immediate(1 << kSmiTagSize)); |
629 __ mov(Operand(ebp, kIndexOffset), eax); | 628 __ mov(Operand(ebp, kIndexOffset), eax); |
630 | 629 |
631 __ bind(&entry); | 630 __ bind(&entry); |
632 __ cmp(eax, Operand(ebp, kLimitOffset)); | 631 __ cmp(eax, Operand(ebp, kLimitOffset)); |
633 __ j(not_equal, &loop); | 632 __ j(not_equal, &loop); |
634 | 633 |
635 // Invoke the function. | 634 // Invoke the function. |
636 ParameterCount actual(eax); | 635 ParameterCount actual(eax); |
637 __ shr(eax, kSmiTagSize); | 636 __ SmiUntag(eax); |
638 __ mov(edi, Operand(ebp, 4 * kPointerSize)); | 637 __ mov(edi, Operand(ebp, 4 * kPointerSize)); |
639 __ InvokeFunction(edi, actual, CALL_FUNCTION); | 638 __ InvokeFunction(edi, actual, CALL_FUNCTION); |
640 | 639 |
641 __ LeaveInternalFrame(); | 640 __ LeaveInternalFrame(); |
642 __ ret(3 * kPointerSize); // remove this, receiver, and arguments | 641 __ ret(3 * kPointerSize); // remove this, receiver, and arguments |
643 } | 642 } |
644 | 643 |
645 | 644 |
646 // Load the built-in Array function from the current context. | 645 // Load the built-in Array function from the current context. |
647 static void GenerateLoadArrayFunction(MacroAssembler* masm, Register result) { | 646 static void GenerateLoadArrayFunction(MacroAssembler* masm, Register result) { |
(...skipping 176 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
824 // array_size: size of array (smi) | 823 // array_size: size of array (smi) |
825 __ lea(elements_array, Operand(result, JSArray::kSize)); | 824 __ lea(elements_array, Operand(result, JSArray::kSize)); |
826 __ mov(FieldOperand(result, JSArray::kElementsOffset), elements_array); | 825 __ mov(FieldOperand(result, JSArray::kElementsOffset), elements_array); |
827 | 826 |
828 // Initialize the fixed array. FixedArray length is not stored as a smi. | 827 // Initialize the fixed array. FixedArray length is not stored as a smi. |
829 // result: JSObject | 828 // result: JSObject |
830 // elements_array: elements array | 829 // elements_array: elements array |
831 // elements_array_end: start of next object | 830 // elements_array_end: start of next object |
832 // array_size: size of array (smi) | 831 // array_size: size of array (smi) |
833 ASSERT(kSmiTag == 0); | 832 ASSERT(kSmiTag == 0); |
834 __ shr(array_size, kSmiTagSize); // Convert from smi to value. | 833 __ SmiUntag(array_size); // Convert from smi to value. |
835 __ mov(FieldOperand(elements_array, JSObject::kMapOffset), | 834 __ mov(FieldOperand(elements_array, JSObject::kMapOffset), |
836 Factory::fixed_array_map()); | 835 Factory::fixed_array_map()); |
837 Label not_empty_2, fill_array; | 836 Label not_empty_2, fill_array; |
838 __ test(array_size, Operand(array_size)); | 837 __ test(array_size, Operand(array_size)); |
839 __ j(not_zero, ¬_empty_2); | 838 __ j(not_zero, ¬_empty_2); |
840 // Length of the FixedArray is the number of pre-allocated elements even | 839 // Length of the FixedArray is the number of pre-allocated elements even |
841 // though the actual JSArray has length 0. | 840 // though the actual JSArray has length 0. |
842 __ mov(FieldOperand(elements_array, Array::kLengthOffset), | 841 __ mov(FieldOperand(elements_array, Array::kLengthOffset), |
843 Immediate(kPreallocatedArrayElements)); | 842 Immediate(kPreallocatedArrayElements)); |
844 __ jmp(&fill_array); | 843 __ jmp(&fill_array); |
(...skipping 108 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
953 __ IncrementCounter(&Counters::array_function_native, 1); | 952 __ IncrementCounter(&Counters::array_function_native, 1); |
954 __ pop(ebx); | 953 __ pop(ebx); |
955 if (construct_call) { | 954 if (construct_call) { |
956 __ pop(edi); | 955 __ pop(edi); |
957 } | 956 } |
958 __ ret(2 * kPointerSize); | 957 __ ret(2 * kPointerSize); |
959 | 958 |
960 // Handle construction of an array from a list of arguments. | 959 // Handle construction of an array from a list of arguments. |
961 __ bind(&argc_two_or_more); | 960 __ bind(&argc_two_or_more); |
962 ASSERT(kSmiTag == 0); | 961 ASSERT(kSmiTag == 0); |
963 __ shl(eax, kSmiTagSize); // Convet argc to a smi. | 962 __ SmiTag(eax); // Convet argc to a smi. |
964 // eax: array_size (smi) | 963 // eax: array_size (smi) |
965 // edi: constructor | 964 // edi: constructor |
966 // esp[0] : argc | 965 // esp[0] : argc |
967 // esp[4]: constructor (only if construct_call) | 966 // esp[4]: constructor (only if construct_call) |
968 // esp[8] : return address | 967 // esp[8] : return address |
969 // esp[C] : last argument | 968 // esp[C] : last argument |
970 AllocateJSArray(masm, | 969 AllocateJSArray(masm, |
971 edi, | 970 edi, |
972 eax, | 971 eax, |
973 ebx, | 972 ebx, |
(...skipping 240 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1214 // Dont adapt arguments. | 1213 // Dont adapt arguments. |
1215 // ------------------------------------------- | 1214 // ------------------------------------------- |
1216 __ bind(&dont_adapt_arguments); | 1215 __ bind(&dont_adapt_arguments); |
1217 __ jmp(Operand(edx)); | 1216 __ jmp(Operand(edx)); |
1218 } | 1217 } |
1219 | 1218 |
1220 | 1219 |
1221 #undef __ | 1220 #undef __ |
1222 | 1221 |
1223 } } // namespace v8::internal | 1222 } } // namespace v8::internal |
OLD | NEW |