OLD | NEW |
1 // Copyright 2010 the V8 project authors. All rights reserved. | 1 // Copyright 2010 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 307 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
318 | 318 |
319 // Handle construction of an empty array. | 319 // Handle construction of an empty array. |
320 AllocateEmptyJSArray(masm, | 320 AllocateEmptyJSArray(masm, |
321 r1, | 321 r1, |
322 r2, | 322 r2, |
323 r3, | 323 r3, |
324 r4, | 324 r4, |
325 r5, | 325 r5, |
326 JSArray::kPreallocatedArrayElements, | 326 JSArray::kPreallocatedArrayElements, |
327 call_generic_code); | 327 call_generic_code); |
328 __ IncrementCounter(&Counters::array_function_native, 1, r3, r4); | 328 __ IncrementCounter(COUNTERS->array_function_native(), 1, r3, r4); |
329 // Setup return value, remove receiver from stack and return. | 329 // Setup return value, remove receiver from stack and return. |
330 __ mov(r0, r2); | 330 __ mov(r0, r2); |
331 __ add(sp, sp, Operand(kPointerSize)); | 331 __ add(sp, sp, Operand(kPointerSize)); |
332 __ Jump(lr); | 332 __ Jump(lr); |
333 | 333 |
334 // Check for one argument. Bail out if argument is not smi or if it is | 334 // Check for one argument. Bail out if argument is not smi or if it is |
335 // negative. | 335 // negative. |
336 __ bind(&argc_one_or_more); | 336 __ bind(&argc_one_or_more); |
337 __ cmp(r0, Operand(1)); | 337 __ cmp(r0, Operand(1)); |
338 __ b(ne, &argc_two_or_more); | 338 __ b(ne, &argc_two_or_more); |
(...skipping 15 matching lines...) Expand all Loading... |
354 AllocateJSArray(masm, | 354 AllocateJSArray(masm, |
355 r1, | 355 r1, |
356 r2, | 356 r2, |
357 r3, | 357 r3, |
358 r4, | 358 r4, |
359 r5, | 359 r5, |
360 r6, | 360 r6, |
361 r7, | 361 r7, |
362 true, | 362 true, |
363 call_generic_code); | 363 call_generic_code); |
364 __ IncrementCounter(&Counters::array_function_native, 1, r2, r4); | 364 __ IncrementCounter(COUNTERS->array_function_native(), 1, r2, r4); |
365 // Setup return value, remove receiver and argument from stack and return. | 365 // Setup return value, remove receiver and argument from stack and return. |
366 __ mov(r0, r3); | 366 __ mov(r0, r3); |
367 __ add(sp, sp, Operand(2 * kPointerSize)); | 367 __ add(sp, sp, Operand(2 * kPointerSize)); |
368 __ Jump(lr); | 368 __ Jump(lr); |
369 | 369 |
370 // Handle construction of an array from a list of arguments. | 370 // Handle construction of an array from a list of arguments. |
371 __ bind(&argc_two_or_more); | 371 __ bind(&argc_two_or_more); |
372 __ mov(r2, Operand(r0, LSL, kSmiTagSize)); // Convet argc to a smi. | 372 __ mov(r2, Operand(r0, LSL, kSmiTagSize)); // Convet argc to a smi. |
373 | 373 |
374 // r0: argc | 374 // r0: argc |
375 // r1: constructor | 375 // r1: constructor |
376 // r2: array_size (smi) | 376 // r2: array_size (smi) |
377 // sp[0]: last argument | 377 // sp[0]: last argument |
378 AllocateJSArray(masm, | 378 AllocateJSArray(masm, |
379 r1, | 379 r1, |
380 r2, | 380 r2, |
381 r3, | 381 r3, |
382 r4, | 382 r4, |
383 r5, | 383 r5, |
384 r6, | 384 r6, |
385 r7, | 385 r7, |
386 false, | 386 false, |
387 call_generic_code); | 387 call_generic_code); |
388 __ IncrementCounter(&Counters::array_function_native, 1, r2, r6); | 388 __ IncrementCounter(COUNTERS->array_function_native(), 1, r2, r6); |
389 | 389 |
390 // Fill arguments as array elements. Copy from the top of the stack (last | 390 // Fill arguments as array elements. Copy from the top of the stack (last |
391 // element) to the array backing store filling it backwards. Note: | 391 // element) to the array backing store filling it backwards. Note: |
392 // elements_array_end points after the backing store therefore PreIndex is | 392 // elements_array_end points after the backing store therefore PreIndex is |
393 // used when filling the backing store. | 393 // used when filling the backing store. |
394 // r0: argc | 394 // r0: argc |
395 // r3: JSArray | 395 // r3: JSArray |
396 // r4: elements_array storage start (untagged) | 396 // r4: elements_array storage start (untagged) |
397 // r5: elements_array_end (untagged) | 397 // r5: elements_array_end (untagged) |
398 // sp[0]: last argument | 398 // sp[0]: last argument |
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
435 __ CompareObjectType(r2, r3, r4, MAP_TYPE); | 435 __ CompareObjectType(r2, r3, r4, MAP_TYPE); |
436 __ Assert(eq, "Unexpected initial map for Array function"); | 436 __ Assert(eq, "Unexpected initial map for Array function"); |
437 } | 437 } |
438 | 438 |
439 // Run the native code for the Array function called as a normal function. | 439 // Run the native code for the Array function called as a normal function. |
440 ArrayNativeCode(masm, &generic_array_code); | 440 ArrayNativeCode(masm, &generic_array_code); |
441 | 441 |
442 // Jump to the generic array code if the specialized code cannot handle | 442 // Jump to the generic array code if the specialized code cannot handle |
443 // the construction. | 443 // the construction. |
444 __ bind(&generic_array_code); | 444 __ bind(&generic_array_code); |
445 Code* code = Builtins::builtin(Builtins::ArrayCodeGeneric); | 445 Code* code = Isolate::Current()->builtins()->builtin( |
| 446 Builtins::ArrayCodeGeneric); |
446 Handle<Code> array_code(code); | 447 Handle<Code> array_code(code); |
447 __ Jump(array_code, RelocInfo::CODE_TARGET); | 448 __ Jump(array_code, RelocInfo::CODE_TARGET); |
448 } | 449 } |
449 | 450 |
450 | 451 |
451 void Builtins::Generate_ArrayConstructCode(MacroAssembler* masm) { | 452 void Builtins::Generate_ArrayConstructCode(MacroAssembler* masm) { |
452 // ----------- S t a t e ------------- | 453 // ----------- S t a t e ------------- |
453 // -- r0 : number of arguments | 454 // -- r0 : number of arguments |
454 // -- r1 : constructor function | 455 // -- r1 : constructor function |
455 // -- lr : return address | 456 // -- lr : return address |
(...skipping 11 matching lines...) Expand all Loading... |
467 __ CompareObjectType(r2, r3, r4, MAP_TYPE); | 468 __ CompareObjectType(r2, r3, r4, MAP_TYPE); |
468 __ Assert(eq, "Unexpected initial map for Array function"); | 469 __ Assert(eq, "Unexpected initial map for Array function"); |
469 } | 470 } |
470 | 471 |
471 // Run the native code for the Array function called as a constructor. | 472 // Run the native code for the Array function called as a constructor. |
472 ArrayNativeCode(masm, &generic_constructor); | 473 ArrayNativeCode(masm, &generic_constructor); |
473 | 474 |
474 // Jump to the generic construct code in case the specialized code cannot | 475 // Jump to the generic construct code in case the specialized code cannot |
475 // handle the construction. | 476 // handle the construction. |
476 __ bind(&generic_constructor); | 477 __ bind(&generic_constructor); |
477 Code* code = Builtins::builtin(Builtins::JSConstructStubGeneric); | 478 Code* code = Isolate::Current()->builtins()->builtin( |
| 479 Builtins::JSConstructStubGeneric); |
478 Handle<Code> generic_construct_stub(code); | 480 Handle<Code> generic_construct_stub(code); |
479 __ Jump(generic_construct_stub, RelocInfo::CODE_TARGET); | 481 __ Jump(generic_construct_stub, RelocInfo::CODE_TARGET); |
480 } | 482 } |
481 | 483 |
482 | 484 |
483 void Builtins::Generate_StringConstructCode(MacroAssembler* masm) { | 485 void Builtins::Generate_StringConstructCode(MacroAssembler* masm) { |
484 // ----------- S t a t e ------------- | 486 // ----------- S t a t e ------------- |
485 // -- r0 : number of arguments | 487 // -- r0 : number of arguments |
486 // -- r1 : constructor function | 488 // -- r1 : constructor function |
487 // -- lr : return address | 489 // -- lr : return address |
488 // -- sp[(argc - n - 1) * 4] : arg[n] (zero based) | 490 // -- sp[(argc - n - 1) * 4] : arg[n] (zero based) |
489 // -- sp[argc * 4] : receiver | 491 // -- sp[argc * 4] : receiver |
490 // ----------------------------------- | 492 // ----------------------------------- |
491 __ IncrementCounter(&Counters::string_ctor_calls, 1, r2, r3); | 493 __ IncrementCounter(COUNTERS->string_ctor_calls(), 1, r2, r3); |
492 | 494 |
493 Register function = r1; | 495 Register function = r1; |
494 if (FLAG_debug_code) { | 496 if (FLAG_debug_code) { |
495 __ LoadGlobalFunction(Context::STRING_FUNCTION_INDEX, r2); | 497 __ LoadGlobalFunction(Context::STRING_FUNCTION_INDEX, r2); |
496 __ cmp(function, Operand(r2)); | 498 __ cmp(function, Operand(r2)); |
497 __ Assert(eq, "Unexpected String function"); | 499 __ Assert(eq, "Unexpected String function"); |
498 } | 500 } |
499 | 501 |
500 // Load the first arguments in r0 and get rid of the rest. | 502 // Load the first arguments in r0 and get rid of the rest. |
501 Label no_arguments; | 503 Label no_arguments; |
502 __ cmp(r0, Operand(0, RelocInfo::NONE)); | 504 __ cmp(r0, Operand(0, RelocInfo::NONE)); |
503 __ b(eq, &no_arguments); | 505 __ b(eq, &no_arguments); |
504 // First args = sp[(argc - 1) * 4]. | 506 // First args = sp[(argc - 1) * 4]. |
505 __ sub(r0, r0, Operand(1)); | 507 __ sub(r0, r0, Operand(1)); |
506 __ ldr(r0, MemOperand(sp, r0, LSL, kPointerSizeLog2, PreIndex)); | 508 __ ldr(r0, MemOperand(sp, r0, LSL, kPointerSizeLog2, PreIndex)); |
507 // sp now point to args[0], drop args[0] + receiver. | 509 // sp now point to args[0], drop args[0] + receiver. |
508 __ Drop(2); | 510 __ Drop(2); |
509 | 511 |
510 Register argument = r2; | 512 Register argument = r2; |
511 Label not_cached, argument_is_string; | 513 Label not_cached, argument_is_string; |
512 NumberToStringStub::GenerateLookupNumberStringCache( | 514 NumberToStringStub::GenerateLookupNumberStringCache( |
513 masm, | 515 masm, |
514 r0, // Input. | 516 r0, // Input. |
515 argument, // Result. | 517 argument, // Result. |
516 r3, // Scratch. | 518 r3, // Scratch. |
517 r4, // Scratch. | 519 r4, // Scratch. |
518 r5, // Scratch. | 520 r5, // Scratch. |
519 false, // Is it a Smi? | 521 false, // Is it a Smi? |
520 ¬_cached); | 522 ¬_cached); |
521 __ IncrementCounter(&Counters::string_ctor_cached_number, 1, r3, r4); | 523 __ IncrementCounter(COUNTERS->string_ctor_cached_number(), 1, r3, r4); |
522 __ bind(&argument_is_string); | 524 __ bind(&argument_is_string); |
523 | 525 |
524 // ----------- S t a t e ------------- | 526 // ----------- S t a t e ------------- |
525 // -- r2 : argument converted to string | 527 // -- r2 : argument converted to string |
526 // -- r1 : constructor function | 528 // -- r1 : constructor function |
527 // -- lr : return address | 529 // -- lr : return address |
528 // ----------------------------------- | 530 // ----------------------------------- |
529 | 531 |
530 Label gc_required; | 532 Label gc_required; |
531 __ AllocateInNewSpace(JSValue::kSize, | 533 __ AllocateInNewSpace(JSValue::kSize, |
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
565 __ bind(¬_cached); | 567 __ bind(¬_cached); |
566 __ JumpIfSmi(r0, &convert_argument); | 568 __ JumpIfSmi(r0, &convert_argument); |
567 | 569 |
568 // Is it a String? | 570 // Is it a String? |
569 __ ldr(r2, FieldMemOperand(r0, HeapObject::kMapOffset)); | 571 __ ldr(r2, FieldMemOperand(r0, HeapObject::kMapOffset)); |
570 __ ldrb(r3, FieldMemOperand(r2, Map::kInstanceTypeOffset)); | 572 __ ldrb(r3, FieldMemOperand(r2, Map::kInstanceTypeOffset)); |
571 ASSERT(kNotStringTag != 0); | 573 ASSERT(kNotStringTag != 0); |
572 __ tst(r3, Operand(kIsNotStringMask)); | 574 __ tst(r3, Operand(kIsNotStringMask)); |
573 __ b(ne, &convert_argument); | 575 __ b(ne, &convert_argument); |
574 __ mov(argument, r0); | 576 __ mov(argument, r0); |
575 __ IncrementCounter(&Counters::string_ctor_conversions, 1, r3, r4); | 577 __ IncrementCounter(COUNTERS->string_ctor_conversions(), 1, r3, r4); |
576 __ b(&argument_is_string); | 578 __ b(&argument_is_string); |
577 | 579 |
578 // Invoke the conversion builtin and put the result into r2. | 580 // Invoke the conversion builtin and put the result into r2. |
579 __ bind(&convert_argument); | 581 __ bind(&convert_argument); |
580 __ push(function); // Preserve the function. | 582 __ push(function); // Preserve the function. |
581 __ IncrementCounter(&Counters::string_ctor_conversions, 1, r3, r4); | 583 __ IncrementCounter(COUNTERS->string_ctor_conversions(), 1, r3, r4); |
582 __ EnterInternalFrame(); | 584 __ EnterInternalFrame(); |
583 __ push(r0); | 585 __ push(r0); |
584 __ InvokeBuiltin(Builtins::TO_STRING, CALL_JS); | 586 __ InvokeBuiltin(Builtins::TO_STRING, CALL_JS); |
585 __ LeaveInternalFrame(); | 587 __ LeaveInternalFrame(); |
586 __ pop(function); | 588 __ pop(function); |
587 __ mov(argument, r0); | 589 __ mov(argument, r0); |
588 __ b(&argument_is_string); | 590 __ b(&argument_is_string); |
589 | 591 |
590 // Load the empty string into r2, remove the receiver from the | 592 // Load the empty string into r2, remove the receiver from the |
591 // stack, and jump back to the case where the argument is a string. | 593 // stack, and jump back to the case where the argument is a string. |
592 __ bind(&no_arguments); | 594 __ bind(&no_arguments); |
593 __ LoadRoot(argument, Heap::kEmptyStringRootIndex); | 595 __ LoadRoot(argument, Heap::kEmptyStringRootIndex); |
594 __ Drop(1); | 596 __ Drop(1); |
595 __ b(&argument_is_string); | 597 __ b(&argument_is_string); |
596 | 598 |
597 // At this point the argument is already a string. Call runtime to | 599 // At this point the argument is already a string. Call runtime to |
598 // create a string wrapper. | 600 // create a string wrapper. |
599 __ bind(&gc_required); | 601 __ bind(&gc_required); |
600 __ IncrementCounter(&Counters::string_ctor_gc_required, 1, r3, r4); | 602 __ IncrementCounter(COUNTERS->string_ctor_gc_required(), 1, r3, r4); |
601 __ EnterInternalFrame(); | 603 __ EnterInternalFrame(); |
602 __ push(argument); | 604 __ push(argument); |
603 __ CallRuntime(Runtime::kNewStringWrapper, 1); | 605 __ CallRuntime(Runtime::kNewStringWrapper, 1); |
604 __ LeaveInternalFrame(); | 606 __ LeaveInternalFrame(); |
605 __ Ret(); | 607 __ Ret(); |
606 } | 608 } |
607 | 609 |
608 | 610 |
609 void Builtins::Generate_JSConstructCall(MacroAssembler* masm) { | 611 void Builtins::Generate_JSConstructCall(MacroAssembler* masm) { |
610 // ----------- S t a t e ------------- | 612 // ----------- S t a t e ------------- |
(...skipping 15 matching lines...) Expand all Loading... |
626 __ ldr(r2, FieldMemOperand(r1, JSFunction::kSharedFunctionInfoOffset)); | 628 __ ldr(r2, FieldMemOperand(r1, JSFunction::kSharedFunctionInfoOffset)); |
627 __ ldr(r2, FieldMemOperand(r2, SharedFunctionInfo::kConstructStubOffset)); | 629 __ ldr(r2, FieldMemOperand(r2, SharedFunctionInfo::kConstructStubOffset)); |
628 __ add(pc, r2, Operand(Code::kHeaderSize - kHeapObjectTag)); | 630 __ add(pc, r2, Operand(Code::kHeaderSize - kHeapObjectTag)); |
629 | 631 |
630 // r0: number of arguments | 632 // r0: number of arguments |
631 // r1: called object | 633 // r1: called object |
632 __ bind(&non_function_call); | 634 __ bind(&non_function_call); |
633 // Set expected number of arguments to zero (not changing r0). | 635 // Set expected number of arguments to zero (not changing r0). |
634 __ mov(r2, Operand(0, RelocInfo::NONE)); | 636 __ mov(r2, Operand(0, RelocInfo::NONE)); |
635 __ GetBuiltinEntry(r3, Builtins::CALL_NON_FUNCTION_AS_CONSTRUCTOR); | 637 __ GetBuiltinEntry(r3, Builtins::CALL_NON_FUNCTION_AS_CONSTRUCTOR); |
636 __ Jump(Handle<Code>(builtin(ArgumentsAdaptorTrampoline)), | 638 __ Jump(Handle<Code>(Isolate::Current()->builtins()->builtin( |
637 RelocInfo::CODE_TARGET); | 639 ArgumentsAdaptorTrampoline)), RelocInfo::CODE_TARGET); |
638 } | 640 } |
639 | 641 |
640 | 642 |
641 static void Generate_JSConstructStubHelper(MacroAssembler* masm, | 643 static void Generate_JSConstructStubHelper(MacroAssembler* masm, |
642 bool is_api_function, | 644 bool is_api_function, |
643 bool count_constructions) { | 645 bool count_constructions) { |
644 // Should never count constructions for api objects. | 646 // Should never count constructions for api objects. |
645 ASSERT(!is_api_function || !count_constructions); | 647 ASSERT(!is_api_function || !count_constructions); |
646 | 648 |
647 // Enter a construct frame. | 649 // Enter a construct frame. |
(...skipping 251 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
899 __ bind(&entry); | 901 __ bind(&entry); |
900 __ sub(r3, r3, Operand(2), SetCC); | 902 __ sub(r3, r3, Operand(2), SetCC); |
901 __ b(ge, &loop); | 903 __ b(ge, &loop); |
902 | 904 |
903 // Call the function. | 905 // Call the function. |
904 // r0: number of arguments | 906 // r0: number of arguments |
905 // r1: constructor function | 907 // r1: constructor function |
906 if (is_api_function) { | 908 if (is_api_function) { |
907 __ ldr(cp, FieldMemOperand(r1, JSFunction::kContextOffset)); | 909 __ ldr(cp, FieldMemOperand(r1, JSFunction::kContextOffset)); |
908 Handle<Code> code = Handle<Code>( | 910 Handle<Code> code = Handle<Code>( |
909 Builtins::builtin(Builtins::HandleApiCallConstruct)); | 911 Isolate::Current()->builtins()->builtin( |
| 912 Builtins::HandleApiCallConstruct)); |
910 ParameterCount expected(0); | 913 ParameterCount expected(0); |
911 __ InvokeCode(code, expected, expected, | 914 __ InvokeCode(code, expected, expected, |
912 RelocInfo::CODE_TARGET, CALL_FUNCTION); | 915 RelocInfo::CODE_TARGET, CALL_FUNCTION); |
913 } else { | 916 } else { |
914 ParameterCount actual(r0); | 917 ParameterCount actual(r0); |
915 __ InvokeFunction(r1, actual, CALL_FUNCTION); | 918 __ InvokeFunction(r1, actual, CALL_FUNCTION); |
916 } | 919 } |
917 | 920 |
918 // Pop the function from the stack. | 921 // Pop the function from the stack. |
919 // sp[0]: constructor function | 922 // sp[0]: constructor function |
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
956 // return. | 959 // return. |
957 __ bind(&exit); | 960 __ bind(&exit); |
958 // r0: result | 961 // r0: result |
959 // sp[0]: receiver (newly allocated object) | 962 // sp[0]: receiver (newly allocated object) |
960 // sp[1]: constructor function | 963 // sp[1]: constructor function |
961 // sp[2]: number of arguments (smi-tagged) | 964 // sp[2]: number of arguments (smi-tagged) |
962 __ ldr(r1, MemOperand(sp, 2 * kPointerSize)); | 965 __ ldr(r1, MemOperand(sp, 2 * kPointerSize)); |
963 __ LeaveConstructFrame(); | 966 __ LeaveConstructFrame(); |
964 __ add(sp, sp, Operand(r1, LSL, kPointerSizeLog2 - 1)); | 967 __ add(sp, sp, Operand(r1, LSL, kPointerSizeLog2 - 1)); |
965 __ add(sp, sp, Operand(kPointerSize)); | 968 __ add(sp, sp, Operand(kPointerSize)); |
966 __ IncrementCounter(&Counters::constructed_objects, 1, r1, r2); | 969 __ IncrementCounter(COUNTERS->constructed_objects(), 1, r1, r2); |
967 __ Jump(lr); | 970 __ Jump(lr); |
968 } | 971 } |
969 | 972 |
970 | 973 |
971 void Builtins::Generate_JSConstructStubCountdown(MacroAssembler* masm) { | 974 void Builtins::Generate_JSConstructStubCountdown(MacroAssembler* masm) { |
972 Generate_JSConstructStubHelper(masm, false, true); | 975 Generate_JSConstructStubHelper(masm, false, true); |
973 } | 976 } |
974 | 977 |
975 | 978 |
976 void Builtins::Generate_JSConstructStubGeneric(MacroAssembler* masm) { | 979 void Builtins::Generate_JSConstructStubGeneric(MacroAssembler* masm) { |
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1032 __ mov(r5, Operand(r4)); | 1035 __ mov(r5, Operand(r4)); |
1033 __ mov(r6, Operand(r4)); | 1036 __ mov(r6, Operand(r4)); |
1034 __ mov(r7, Operand(r4)); | 1037 __ mov(r7, Operand(r4)); |
1035 if (kR9Available == 1) { | 1038 if (kR9Available == 1) { |
1036 __ mov(r9, Operand(r4)); | 1039 __ mov(r9, Operand(r4)); |
1037 } | 1040 } |
1038 | 1041 |
1039 // Invoke the code and pass argc as r0. | 1042 // Invoke the code and pass argc as r0. |
1040 __ mov(r0, Operand(r3)); | 1043 __ mov(r0, Operand(r3)); |
1041 if (is_construct) { | 1044 if (is_construct) { |
1042 __ Call(Handle<Code>(Builtins::builtin(Builtins::JSConstructCall)), | 1045 __ Call(Handle<Code>(Isolate::Current()->builtins()->builtin( |
1043 RelocInfo::CODE_TARGET); | 1046 Builtins::JSConstructCall)), RelocInfo::CODE_TARGET); |
1044 } else { | 1047 } else { |
1045 ParameterCount actual(r0); | 1048 ParameterCount actual(r0); |
1046 __ InvokeFunction(r1, actual, CALL_FUNCTION); | 1049 __ InvokeFunction(r1, actual, CALL_FUNCTION); |
1047 } | 1050 } |
1048 | 1051 |
1049 // Exit the JS frame and remove the parameters (except function), and return. | 1052 // Exit the JS frame and remove the parameters (except function), and return. |
1050 // Respect ABI stack constraint. | 1053 // Respect ABI stack constraint. |
1051 __ LeaveInternalFrame(); | 1054 __ LeaveInternalFrame(); |
1052 __ Jump(lr); | 1055 __ Jump(lr); |
1053 | 1056 |
(...skipping 108 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1162 __ CallRuntime(Runtime::kNotifyOSR, 0); | 1165 __ CallRuntime(Runtime::kNotifyOSR, 0); |
1163 __ LeaveInternalFrame(); | 1166 __ LeaveInternalFrame(); |
1164 __ ldm(ia_w, sp, kJSCallerSaved | kCalleeSaved | lr.bit() | fp.bit()); | 1167 __ ldm(ia_w, sp, kJSCallerSaved | kCalleeSaved | lr.bit() | fp.bit()); |
1165 __ Ret(); | 1168 __ Ret(); |
1166 } | 1169 } |
1167 | 1170 |
1168 | 1171 |
1169 void Builtins::Generate_OnStackReplacement(MacroAssembler* masm) { | 1172 void Builtins::Generate_OnStackReplacement(MacroAssembler* masm) { |
1170 // Probe the CPU to set the supported features, because this builtin | 1173 // Probe the CPU to set the supported features, because this builtin |
1171 // may be called before the initialization performs CPU setup. | 1174 // may be called before the initialization performs CPU setup. |
1172 CpuFeatures::Probe(false); | 1175 Isolate::Current()->cpu_features()->Probe(false); |
1173 | 1176 |
1174 // Lookup the function in the JavaScript frame and push it as an | 1177 // Lookup the function in the JavaScript frame and push it as an |
1175 // argument to the on-stack replacement function. | 1178 // argument to the on-stack replacement function. |
1176 __ ldr(r0, MemOperand(fp, JavaScriptFrameConstants::kFunctionOffset)); | 1179 __ ldr(r0, MemOperand(fp, JavaScriptFrameConstants::kFunctionOffset)); |
1177 __ EnterInternalFrame(); | 1180 __ EnterInternalFrame(); |
1178 __ push(r0); | 1181 __ push(r0); |
1179 __ CallRuntime(Runtime::kCompileForOnStackReplacement, 1); | 1182 __ CallRuntime(Runtime::kCompileForOnStackReplacement, 1); |
1180 __ LeaveInternalFrame(); | 1183 __ LeaveInternalFrame(); |
1181 | 1184 |
1182 // If the result was -1 it means that we couldn't optimize the | 1185 // If the result was -1 it means that we couldn't optimize the |
(...skipping 142 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1325 | 1328 |
1326 // 5a. Call non-function via tail call to CALL_NON_FUNCTION builtin. | 1329 // 5a. Call non-function via tail call to CALL_NON_FUNCTION builtin. |
1327 // r0: actual number of arguments | 1330 // r0: actual number of arguments |
1328 // r1: function | 1331 // r1: function |
1329 { Label function; | 1332 { Label function; |
1330 __ tst(r1, r1); | 1333 __ tst(r1, r1); |
1331 __ b(ne, &function); | 1334 __ b(ne, &function); |
1332 // Expected number of arguments is 0 for CALL_NON_FUNCTION. | 1335 // Expected number of arguments is 0 for CALL_NON_FUNCTION. |
1333 __ mov(r2, Operand(0, RelocInfo::NONE)); | 1336 __ mov(r2, Operand(0, RelocInfo::NONE)); |
1334 __ GetBuiltinEntry(r3, Builtins::CALL_NON_FUNCTION); | 1337 __ GetBuiltinEntry(r3, Builtins::CALL_NON_FUNCTION); |
1335 __ Jump(Handle<Code>(builtin(ArgumentsAdaptorTrampoline)), | 1338 __ Jump(Handle<Code>(Isolate::Current()->builtins()->builtin( |
1336 RelocInfo::CODE_TARGET); | 1339 ArgumentsAdaptorTrampoline)), RelocInfo::CODE_TARGET); |
1337 __ bind(&function); | 1340 __ bind(&function); |
1338 } | 1341 } |
1339 | 1342 |
1340 // 5b. Get the code to call from the function and check that the number of | 1343 // 5b. Get the code to call from the function and check that the number of |
1341 // expected arguments matches what we're providing. If so, jump | 1344 // expected arguments matches what we're providing. If so, jump |
1342 // (tail-call) to the code in register edx without checking arguments. | 1345 // (tail-call) to the code in register edx without checking arguments. |
1343 // r0: actual number of arguments | 1346 // r0: actual number of arguments |
1344 // r1: function | 1347 // r1: function |
1345 __ ldr(r3, FieldMemOperand(r1, JSFunction::kSharedFunctionInfoOffset)); | 1348 __ ldr(r3, FieldMemOperand(r1, JSFunction::kSharedFunctionInfoOffset)); |
1346 __ ldr(r2, | 1349 __ ldr(r2, |
1347 FieldMemOperand(r3, SharedFunctionInfo::kFormalParameterCountOffset)); | 1350 FieldMemOperand(r3, SharedFunctionInfo::kFormalParameterCountOffset)); |
1348 __ mov(r2, Operand(r2, ASR, kSmiTagSize)); | 1351 __ mov(r2, Operand(r2, ASR, kSmiTagSize)); |
1349 __ ldr(r3, FieldMemOperand(r1, JSFunction::kCodeEntryOffset)); | 1352 __ ldr(r3, FieldMemOperand(r1, JSFunction::kCodeEntryOffset)); |
1350 __ cmp(r2, r0); // Check formal and actual parameter counts. | 1353 __ cmp(r2, r0); // Check formal and actual parameter counts. |
1351 __ Jump(Handle<Code>(builtin(ArgumentsAdaptorTrampoline)), | 1354 __ Jump(Handle<Code>(Isolate::Current()->builtins()->builtin( |
1352 RelocInfo::CODE_TARGET, ne); | 1355 ArgumentsAdaptorTrampoline)), RelocInfo::CODE_TARGET, ne); |
1353 | 1356 |
1354 ParameterCount expected(0); | 1357 ParameterCount expected(0); |
1355 __ InvokeCode(r3, expected, expected, JUMP_FUNCTION); | 1358 __ InvokeCode(r3, expected, expected, JUMP_FUNCTION); |
1356 } | 1359 } |
1357 | 1360 |
1358 | 1361 |
1359 void Builtins::Generate_FunctionApply(MacroAssembler* masm) { | 1362 void Builtins::Generate_FunctionApply(MacroAssembler* masm) { |
1360 const int kIndexOffset = -5 * kPointerSize; | 1363 const int kIndexOffset = -5 * kPointerSize; |
1361 const int kLimitOffset = -4 * kPointerSize; | 1364 const int kLimitOffset = -4 * kPointerSize; |
1362 const int kArgsOffset = 2 * kPointerSize; | 1365 const int kArgsOffset = 2 * kPointerSize; |
(...skipping 253 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1616 __ bind(&dont_adapt_arguments); | 1619 __ bind(&dont_adapt_arguments); |
1617 __ Jump(r3); | 1620 __ Jump(r3); |
1618 } | 1621 } |
1619 | 1622 |
1620 | 1623 |
1621 #undef __ | 1624 #undef __ |
1622 | 1625 |
1623 } } // namespace v8::internal | 1626 } } // namespace v8::internal |
1624 | 1627 |
1625 #endif // V8_TARGET_ARCH_ARM | 1628 #endif // V8_TARGET_ARCH_ARM |
OLD | NEW |