Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(967)

Side by Side Diff: src/ia32/code-stubs-ia32.cc

Issue 7745022: Changed some jumps to short jumps in IA32 generated code. (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Fixed one jump that mustn't be a short jump. Created 9 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2011 the V8 project authors. All rights reserved. 1 // Copyright 2011 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 475 matching lines...) Expand 10 before | Expand all | Expand 10 after
486 __ xor_(ecx, Operand(ecx)); 486 __ xor_(ecx, Operand(ecx));
487 // Check whether the exponent matches a 32 bit signed int that cannot be 487 // Check whether the exponent matches a 32 bit signed int that cannot be
488 // represented by a Smi. A non-smi 32 bit integer is 1.xxx * 2^30 so the 488 // represented by a Smi. A non-smi 32 bit integer is 1.xxx * 2^30 so the
489 // exponent is 30 (biased). This is the exponent that we are fastest at and 489 // exponent is 30 (biased). This is the exponent that we are fastest at and
490 // also the highest exponent we can handle here. 490 // also the highest exponent we can handle here.
491 const uint32_t non_smi_exponent = 491 const uint32_t non_smi_exponent =
492 (HeapNumber::kExponentBias + 30) << HeapNumber::kExponentShift; 492 (HeapNumber::kExponentBias + 30) << HeapNumber::kExponentShift;
493 __ cmp(Operand(scratch2), Immediate(non_smi_exponent)); 493 __ cmp(Operand(scratch2), Immediate(non_smi_exponent));
494 // If we have a match of the int32-but-not-Smi exponent then skip some 494 // If we have a match of the int32-but-not-Smi exponent then skip some
495 // logic. 495 // logic.
496 __ j(equal, &right_exponent); 496 __ j(equal, &right_exponent, Label::kNear);
497 // If the exponent is higher than that then go to slow case. This catches 497 // If the exponent is higher than that then go to slow case. This catches
498 // numbers that don't fit in a signed int32, infinities and NaNs. 498 // numbers that don't fit in a signed int32, infinities and NaNs.
499 __ j(less, &normal_exponent); 499 __ j(less, &normal_exponent, Label::kNear);
500 500
501 { 501 {
502 // Handle a big exponent. The only reason we have this code is that the 502 // Handle a big exponent. The only reason we have this code is that the
503 // >>> operator has a tendency to generate numbers with an exponent of 31. 503 // >>> operator has a tendency to generate numbers with an exponent of 31.
504 const uint32_t big_non_smi_exponent = 504 const uint32_t big_non_smi_exponent =
505 (HeapNumber::kExponentBias + 31) << HeapNumber::kExponentShift; 505 (HeapNumber::kExponentBias + 31) << HeapNumber::kExponentShift;
506 __ cmp(Operand(scratch2), Immediate(big_non_smi_exponent)); 506 __ cmp(Operand(scratch2), Immediate(big_non_smi_exponent));
507 __ j(not_equal, conversion_failure); 507 __ j(not_equal, conversion_failure);
508 // We have the big exponent, typically from >>>. This means the number is 508 // We have the big exponent, typically from >>>. This means the number is
509 // in the range 2^31 to 2^32 - 1. Get the top bits of the mantissa. 509 // in the range 2^31 to 2^32 - 1. Get the top bits of the mantissa.
510 __ mov(scratch2, scratch); 510 __ mov(scratch2, scratch);
511 __ and_(scratch2, HeapNumber::kMantissaMask); 511 __ and_(scratch2, HeapNumber::kMantissaMask);
512 // Put back the implicit 1. 512 // Put back the implicit 1.
513 __ or_(scratch2, 1 << HeapNumber::kExponentShift); 513 __ or_(scratch2, 1 << HeapNumber::kExponentShift);
514 // Shift up the mantissa bits to take up the space the exponent used to 514 // Shift up the mantissa bits to take up the space the exponent used to
515 // take. We just orred in the implicit bit so that took care of one and 515 // take. We just orred in the implicit bit so that took care of one and
516 // we want to use the full unsigned range so we subtract 1 bit from the 516 // we want to use the full unsigned range so we subtract 1 bit from the
517 // shift distance. 517 // shift distance.
518 const int big_shift_distance = HeapNumber::kNonMantissaBitsInTopWord - 1; 518 const int big_shift_distance = HeapNumber::kNonMantissaBitsInTopWord - 1;
519 __ shl(scratch2, big_shift_distance); 519 __ shl(scratch2, big_shift_distance);
520 // Get the second half of the double. 520 // Get the second half of the double.
521 __ mov(ecx, FieldOperand(source, HeapNumber::kMantissaOffset)); 521 __ mov(ecx, FieldOperand(source, HeapNumber::kMantissaOffset));
522 // Shift down 21 bits to get the most significant 11 bits or the low 522 // Shift down 21 bits to get the most significant 11 bits or the low
523 // mantissa word. 523 // mantissa word.
524 __ shr(ecx, 32 - big_shift_distance); 524 __ shr(ecx, 32 - big_shift_distance);
525 __ or_(ecx, Operand(scratch2)); 525 __ or_(ecx, Operand(scratch2));
526 // We have the answer in ecx, but we may need to negate it. 526 // We have the answer in ecx, but we may need to negate it.
527 __ test(scratch, Operand(scratch)); 527 __ test(scratch, Operand(scratch));
528 __ j(positive, &done); 528 __ j(positive, &done, Label::kNear);
529 __ neg(ecx); 529 __ neg(ecx);
530 __ jmp(&done); 530 __ jmp(&done, Label::kNear);
531 } 531 }
532 532
533 __ bind(&normal_exponent); 533 __ bind(&normal_exponent);
534 // Exponent word in scratch, exponent part of exponent word in scratch2. 534 // Exponent word in scratch, exponent part of exponent word in scratch2.
535 // Zero in ecx. 535 // Zero in ecx.
536 // We know the exponent is smaller than 30 (biased). If it is less than 536 // We know the exponent is smaller than 30 (biased). If it is less than
537 // 0 (biased) then the number is smaller in magnitude than 1.0 * 2^0, ie 537 // 0 (biased) then the number is smaller in magnitude than 1.0 * 2^0, ie
538 // it rounds to zero. 538 // it rounds to zero.
539 const uint32_t zero_exponent = 539 const uint32_t zero_exponent =
540 (HeapNumber::kExponentBias + 0) << HeapNumber::kExponentShift; 540 (HeapNumber::kExponentBias + 0) << HeapNumber::kExponentShift;
541 __ sub(Operand(scratch2), Immediate(zero_exponent)); 541 __ sub(Operand(scratch2), Immediate(zero_exponent));
542 // ecx already has a Smi zero. 542 // ecx already has a Smi zero.
543 __ j(less, &done); 543 __ j(less, &done, Label::kNear);
544 544
545 // We have a shifted exponent between 0 and 30 in scratch2. 545 // We have a shifted exponent between 0 and 30 in scratch2.
546 __ shr(scratch2, HeapNumber::kExponentShift); 546 __ shr(scratch2, HeapNumber::kExponentShift);
547 __ mov(ecx, Immediate(30)); 547 __ mov(ecx, Immediate(30));
548 __ sub(ecx, Operand(scratch2)); 548 __ sub(ecx, Operand(scratch2));
549 549
550 __ bind(&right_exponent); 550 __ bind(&right_exponent);
551 // Here ecx is the shift, scratch is the exponent word. 551 // Here ecx is the shift, scratch is the exponent word.
552 // Get the top bits of the mantissa. 552 // Get the top bits of the mantissa.
553 __ and_(scratch, HeapNumber::kMantissaMask); 553 __ and_(scratch, HeapNumber::kMantissaMask);
(...skipping 204 matching lines...) Expand 10 before | Expand all | Expand 10 after
758 758
759 if (mode_ == UNARY_OVERWRITE) { 759 if (mode_ == UNARY_OVERWRITE) {
760 __ xor_(FieldOperand(eax, HeapNumber::kExponentOffset), 760 __ xor_(FieldOperand(eax, HeapNumber::kExponentOffset),
761 Immediate(HeapNumber::kSignMask)); // Flip sign. 761 Immediate(HeapNumber::kSignMask)); // Flip sign.
762 } else { 762 } else {
763 __ mov(edx, Operand(eax)); 763 __ mov(edx, Operand(eax));
764 // edx: operand 764 // edx: operand
765 765
766 Label slow_allocate_heapnumber, heapnumber_allocated; 766 Label slow_allocate_heapnumber, heapnumber_allocated;
767 __ AllocateHeapNumber(eax, ebx, ecx, &slow_allocate_heapnumber); 767 __ AllocateHeapNumber(eax, ebx, ecx, &slow_allocate_heapnumber);
768 __ jmp(&heapnumber_allocated); 768 __ jmp(&heapnumber_allocated, Label::kNear);
769 769
770 __ bind(&slow_allocate_heapnumber); 770 __ bind(&slow_allocate_heapnumber);
771 __ EnterInternalFrame(); 771 __ EnterInternalFrame();
772 __ push(edx); 772 __ push(edx);
773 __ CallRuntime(Runtime::kNumberAlloc, 0); 773 __ CallRuntime(Runtime::kNumberAlloc, 0);
774 __ pop(edx); 774 __ pop(edx);
775 __ LeaveInternalFrame(); 775 __ LeaveInternalFrame();
776 776
777 __ bind(&heapnumber_allocated); 777 __ bind(&heapnumber_allocated);
778 // eax: allocated 'empty' number 778 // eax: allocated 'empty' number
(...skipping 656 matching lines...) Expand 10 before | Expand all | Expand 10 after
1435 ASSERT(operands_type_ == BinaryOpIC::BOTH_STRING); 1435 ASSERT(operands_type_ == BinaryOpIC::BOTH_STRING);
1436 ASSERT(op_ == Token::ADD); 1436 ASSERT(op_ == Token::ADD);
1437 // If both arguments are strings, call the string add stub. 1437 // If both arguments are strings, call the string add stub.
1438 // Otherwise, do a transition. 1438 // Otherwise, do a transition.
1439 1439
1440 // Registers containing left and right operands respectively. 1440 // Registers containing left and right operands respectively.
1441 Register left = edx; 1441 Register left = edx;
1442 Register right = eax; 1442 Register right = eax;
1443 1443
1444 // Test if left operand is a string. 1444 // Test if left operand is a string.
1445 __ JumpIfSmi(left, &call_runtime); 1445 __ JumpIfSmi(left, &call_runtime, Label::kNear);
1446 __ CmpObjectType(left, FIRST_NONSTRING_TYPE, ecx); 1446 __ CmpObjectType(left, FIRST_NONSTRING_TYPE, ecx);
1447 __ j(above_equal, &call_runtime); 1447 __ j(above_equal, &call_runtime, Label::kNear);
1448 1448
1449 // Test if right operand is a string. 1449 // Test if right operand is a string.
1450 __ JumpIfSmi(right, &call_runtime); 1450 __ JumpIfSmi(right, &call_runtime, Label::kNear);
1451 __ CmpObjectType(right, FIRST_NONSTRING_TYPE, ecx); 1451 __ CmpObjectType(right, FIRST_NONSTRING_TYPE, ecx);
1452 __ j(above_equal, &call_runtime); 1452 __ j(above_equal, &call_runtime, Label::kNear);
1453 1453
1454 StringAddStub string_add_stub(NO_STRING_CHECK_IN_STUB); 1454 StringAddStub string_add_stub(NO_STRING_CHECK_IN_STUB);
1455 GenerateRegisterArgsPush(masm); 1455 GenerateRegisterArgsPush(masm);
1456 __ TailCallStub(&string_add_stub); 1456 __ TailCallStub(&string_add_stub);
1457 1457
1458 __ bind(&call_runtime); 1458 __ bind(&call_runtime);
1459 GenerateTypeTransition(masm); 1459 GenerateTypeTransition(masm);
1460 } 1460 }
1461 1461
1462 1462
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after
1556 case Token::SHR: __ shr_cl(eax); break; 1556 case Token::SHR: __ shr_cl(eax); break;
1557 default: UNREACHABLE(); 1557 default: UNREACHABLE();
1558 } 1558 }
1559 if (op_ == Token::SHR) { 1559 if (op_ == Token::SHR) {
1560 // Check if result is non-negative and fits in a smi. 1560 // Check if result is non-negative and fits in a smi.
1561 __ test(eax, Immediate(0xc0000000)); 1561 __ test(eax, Immediate(0xc0000000));
1562 __ j(not_zero, &call_runtime); 1562 __ j(not_zero, &call_runtime);
1563 } else { 1563 } else {
1564 // Check if result fits in a smi. 1564 // Check if result fits in a smi.
1565 __ cmp(eax, 0xc0000000); 1565 __ cmp(eax, 0xc0000000);
1566 __ j(negative, &non_smi_result); 1566 __ j(negative, &non_smi_result, Label::kNear);
1567 } 1567 }
1568 // Tag smi result and return. 1568 // Tag smi result and return.
1569 __ SmiTag(eax); 1569 __ SmiTag(eax);
1570 __ ret(2 * kPointerSize); // Drop two pushed arguments from the stack. 1570 __ ret(2 * kPointerSize); // Drop two pushed arguments from the stack.
1571 1571
1572 // All ops except SHR return a signed int32 that we load in 1572 // All ops except SHR return a signed int32 that we load in
1573 // a HeapNumber. 1573 // a HeapNumber.
1574 if (op_ != Token::SHR) { 1574 if (op_ != Token::SHR) {
1575 __ bind(&non_smi_result); 1575 __ bind(&non_smi_result);
1576 // Allocate a heap number if needed. 1576 // Allocate a heap number if needed.
(...skipping 193 matching lines...) Expand 10 before | Expand all | Expand 10 after
1770 case Token::SHR: __ shr_cl(eax); break; 1770 case Token::SHR: __ shr_cl(eax); break;
1771 default: UNREACHABLE(); 1771 default: UNREACHABLE();
1772 } 1772 }
1773 if (op_ == Token::SHR) { 1773 if (op_ == Token::SHR) {
1774 // Check if result is non-negative and fits in a smi. 1774 // Check if result is non-negative and fits in a smi.
1775 __ test(eax, Immediate(0xc0000000)); 1775 __ test(eax, Immediate(0xc0000000));
1776 __ j(not_zero, &call_runtime); 1776 __ j(not_zero, &call_runtime);
1777 } else { 1777 } else {
1778 // Check if result fits in a smi. 1778 // Check if result fits in a smi.
1779 __ cmp(eax, 0xc0000000); 1779 __ cmp(eax, 0xc0000000);
1780 __ j(negative, &non_smi_result); 1780 __ j(negative, &non_smi_result, Label::kNear);
1781 } 1781 }
1782 // Tag smi result and return. 1782 // Tag smi result and return.
1783 __ SmiTag(eax); 1783 __ SmiTag(eax);
1784 __ ret(2 * kPointerSize); // Drop two pushed arguments from the stack. 1784 __ ret(2 * kPointerSize); // Drop two pushed arguments from the stack.
1785 1785
1786 // All ops except SHR return a signed int32 that we load in 1786 // All ops except SHR return a signed int32 that we load in
1787 // a HeapNumber. 1787 // a HeapNumber.
1788 if (op_ != Token::SHR) { 1788 if (op_ != Token::SHR) {
1789 __ bind(&non_smi_result); 1789 __ bind(&non_smi_result);
1790 // Allocate a heap number if needed. 1790 // Allocate a heap number if needed.
(...skipping 178 matching lines...) Expand 10 before | Expand all | Expand 10 after
1969 case Token::SHR: __ shr_cl(eax); break; 1969 case Token::SHR: __ shr_cl(eax); break;
1970 default: UNREACHABLE(); 1970 default: UNREACHABLE();
1971 } 1971 }
1972 if (op_ == Token::SHR) { 1972 if (op_ == Token::SHR) {
1973 // Check if result is non-negative and fits in a smi. 1973 // Check if result is non-negative and fits in a smi.
1974 __ test(eax, Immediate(0xc0000000)); 1974 __ test(eax, Immediate(0xc0000000));
1975 __ j(not_zero, &call_runtime); 1975 __ j(not_zero, &call_runtime);
1976 } else { 1976 } else {
1977 // Check if result fits in a smi. 1977 // Check if result fits in a smi.
1978 __ cmp(eax, 0xc0000000); 1978 __ cmp(eax, 0xc0000000);
1979 __ j(negative, &non_smi_result); 1979 __ j(negative, &non_smi_result, Label::kNear);
1980 } 1980 }
1981 // Tag smi result and return. 1981 // Tag smi result and return.
1982 __ SmiTag(eax); 1982 __ SmiTag(eax);
1983 __ ret(2 * kPointerSize); // Drop the arguments from the stack. 1983 __ ret(2 * kPointerSize); // Drop the arguments from the stack.
1984 1984
1985 // All ops except SHR return a signed int32 that we load in 1985 // All ops except SHR return a signed int32 that we load in
1986 // a HeapNumber. 1986 // a HeapNumber.
1987 if (op_ != Token::SHR) { 1987 if (op_ != Token::SHR) {
1988 __ bind(&non_smi_result); 1988 __ bind(&non_smi_result);
1989 // Allocate a heap number if needed. 1989 // Allocate a heap number if needed.
(...skipping 454 matching lines...) Expand 10 before | Expand all | Expand 10 after
2444 // Output: eax, ecx are left and right integers for a bit op. 2444 // Output: eax, ecx are left and right integers for a bit op.
2445 void FloatingPointHelper::LoadUnknownsAsIntegers(MacroAssembler* masm, 2445 void FloatingPointHelper::LoadUnknownsAsIntegers(MacroAssembler* masm,
2446 bool use_sse3, 2446 bool use_sse3,
2447 Label* conversion_failure) { 2447 Label* conversion_failure) {
2448 // Check float operands. 2448 // Check float operands.
2449 Label arg1_is_object, check_undefined_arg1; 2449 Label arg1_is_object, check_undefined_arg1;
2450 Label arg2_is_object, check_undefined_arg2; 2450 Label arg2_is_object, check_undefined_arg2;
2451 Label load_arg2, done; 2451 Label load_arg2, done;
2452 2452
2453 // Test if arg1 is a Smi. 2453 // Test if arg1 is a Smi.
2454 __ JumpIfNotSmi(edx, &arg1_is_object); 2454 __ JumpIfNotSmi(edx, &arg1_is_object, Label::kNear);
2455 2455
2456 __ SmiUntag(edx); 2456 __ SmiUntag(edx);
2457 __ jmp(&load_arg2); 2457 __ jmp(&load_arg2, Label::kNear);
2458 2458
2459 // If the argument is undefined it converts to zero (ECMA-262, section 9.5). 2459 // If the argument is undefined it converts to zero (ECMA-262, section 9.5).
2460 __ bind(&check_undefined_arg1); 2460 __ bind(&check_undefined_arg1);
2461 Factory* factory = masm->isolate()->factory(); 2461 Factory* factory = masm->isolate()->factory();
2462 __ cmp(edx, factory->undefined_value()); 2462 __ cmp(edx, factory->undefined_value());
2463 __ j(not_equal, conversion_failure); 2463 __ j(not_equal, conversion_failure);
2464 __ mov(edx, Immediate(0)); 2464 __ mov(edx, Immediate(0));
2465 __ jmp(&load_arg2); 2465 __ jmp(&load_arg2, Label::kNear);
2466 2466
2467 __ bind(&arg1_is_object); 2467 __ bind(&arg1_is_object);
2468 __ mov(ebx, FieldOperand(edx, HeapObject::kMapOffset)); 2468 __ mov(ebx, FieldOperand(edx, HeapObject::kMapOffset));
2469 __ cmp(ebx, factory->heap_number_map()); 2469 __ cmp(ebx, factory->heap_number_map());
2470 __ j(not_equal, &check_undefined_arg1); 2470 __ j(not_equal, &check_undefined_arg1);
2471 2471
2472 // Get the untagged integer version of the edx heap number in ecx. 2472 // Get the untagged integer version of the edx heap number in ecx.
2473 IntegerConvert(masm, edx, use_sse3, conversion_failure); 2473 IntegerConvert(masm, edx, use_sse3, conversion_failure);
2474 __ mov(edx, ecx); 2474 __ mov(edx, ecx);
2475 2475
2476 // Here edx has the untagged integer, eax has a Smi or a heap number. 2476 // Here edx has the untagged integer, eax has a Smi or a heap number.
2477 __ bind(&load_arg2); 2477 __ bind(&load_arg2);
2478 2478
2479 // Test if arg2 is a Smi. 2479 // Test if arg2 is a Smi.
2480 __ JumpIfNotSmi(eax, &arg2_is_object); 2480 __ JumpIfNotSmi(eax, &arg2_is_object, Label::kNear);
2481 2481
2482 __ SmiUntag(eax); 2482 __ SmiUntag(eax);
2483 __ mov(ecx, eax); 2483 __ mov(ecx, eax);
2484 __ jmp(&done); 2484 __ jmp(&done, Label::kNear);
2485 2485
2486 // If the argument is undefined it converts to zero (ECMA-262, section 9.5). 2486 // If the argument is undefined it converts to zero (ECMA-262, section 9.5).
2487 __ bind(&check_undefined_arg2); 2487 __ bind(&check_undefined_arg2);
2488 __ cmp(eax, factory->undefined_value()); 2488 __ cmp(eax, factory->undefined_value());
2489 __ j(not_equal, conversion_failure); 2489 __ j(not_equal, conversion_failure);
2490 __ mov(ecx, Immediate(0)); 2490 __ mov(ecx, Immediate(0));
2491 __ jmp(&done); 2491 __ jmp(&done, Label::kNear);
2492 2492
2493 __ bind(&arg2_is_object); 2493 __ bind(&arg2_is_object);
2494 __ mov(ebx, FieldOperand(eax, HeapObject::kMapOffset)); 2494 __ mov(ebx, FieldOperand(eax, HeapObject::kMapOffset));
2495 __ cmp(ebx, factory->heap_number_map()); 2495 __ cmp(ebx, factory->heap_number_map());
2496 __ j(not_equal, &check_undefined_arg2); 2496 __ j(not_equal, &check_undefined_arg2);
2497 2497
2498 // Get the untagged integer version of the eax heap number in ecx. 2498 // Get the untagged integer version of the eax heap number in ecx.
2499 IntegerConvert(masm, eax, use_sse3, conversion_failure); 2499 IntegerConvert(masm, eax, use_sse3, conversion_failure);
2500 __ bind(&done); 2500 __ bind(&done);
2501 __ mov(eax, edx); 2501 __ mov(eax, edx);
(...skipping 358 matching lines...) Expand 10 before | Expand all | Expand 10 after
2860 void ArgumentsAccessStub::GenerateReadElement(MacroAssembler* masm) { 2860 void ArgumentsAccessStub::GenerateReadElement(MacroAssembler* masm) {
2861 // The key is in edx and the parameter count is in eax. 2861 // The key is in edx and the parameter count is in eax.
2862 2862
2863 // The displacement is used for skipping the frame pointer on the 2863 // The displacement is used for skipping the frame pointer on the
2864 // stack. It is the offset of the last parameter (if any) relative 2864 // stack. It is the offset of the last parameter (if any) relative
2865 // to the frame pointer. 2865 // to the frame pointer.
2866 static const int kDisplacement = 1 * kPointerSize; 2866 static const int kDisplacement = 1 * kPointerSize;
2867 2867
2868 // Check that the key is a smi. 2868 // Check that the key is a smi.
2869 Label slow; 2869 Label slow;
2870 __ JumpIfNotSmi(edx, &slow); 2870 __ JumpIfNotSmi(edx, &slow, Label::kNear);
2871 2871
2872 // Check if the calling frame is an arguments adaptor frame. 2872 // Check if the calling frame is an arguments adaptor frame.
2873 Label adaptor; 2873 Label adaptor;
2874 __ mov(ebx, Operand(ebp, StandardFrameConstants::kCallerFPOffset)); 2874 __ mov(ebx, Operand(ebp, StandardFrameConstants::kCallerFPOffset));
2875 __ mov(ecx, Operand(ebx, StandardFrameConstants::kContextOffset)); 2875 __ mov(ecx, Operand(ebx, StandardFrameConstants::kContextOffset));
2876 __ cmp(Operand(ecx), Immediate(Smi::FromInt(StackFrame::ARGUMENTS_ADAPTOR))); 2876 __ cmp(Operand(ecx), Immediate(Smi::FromInt(StackFrame::ARGUMENTS_ADAPTOR)));
2877 __ j(equal, &adaptor, Label::kNear); 2877 __ j(equal, &adaptor, Label::kNear);
2878 2878
2879 // Check index against formal parameters count limit passed in 2879 // Check index against formal parameters count limit passed in
2880 // through register eax. Use unsigned comparison to get negative 2880 // through register eax. Use unsigned comparison to get negative
2881 // check for free. 2881 // check for free.
2882 __ cmp(edx, Operand(eax)); 2882 __ cmp(edx, Operand(eax));
2883 __ j(above_equal, &slow); 2883 __ j(above_equal, &slow, Label::kNear);
2884 2884
2885 // Read the argument from the stack and return it. 2885 // Read the argument from the stack and return it.
2886 STATIC_ASSERT(kSmiTagSize == 1); 2886 STATIC_ASSERT(kSmiTagSize == 1);
2887 STATIC_ASSERT(kSmiTag == 0); // Shifting code depends on these. 2887 STATIC_ASSERT(kSmiTag == 0); // Shifting code depends on these.
2888 __ lea(ebx, Operand(ebp, eax, times_2, 0)); 2888 __ lea(ebx, Operand(ebp, eax, times_2, 0));
2889 __ neg(edx); 2889 __ neg(edx);
2890 __ mov(eax, Operand(ebx, edx, times_2, kDisplacement)); 2890 __ mov(eax, Operand(ebx, edx, times_2, kDisplacement));
2891 __ ret(0); 2891 __ ret(0);
2892 2892
2893 // Arguments adaptor case: Check index against actual arguments 2893 // Arguments adaptor case: Check index against actual arguments
2894 // limit found in the arguments adaptor frame. Use unsigned 2894 // limit found in the arguments adaptor frame. Use unsigned
2895 // comparison to get negative check for free. 2895 // comparison to get negative check for free.
2896 __ bind(&adaptor); 2896 __ bind(&adaptor);
2897 __ mov(ecx, Operand(ebx, ArgumentsAdaptorFrameConstants::kLengthOffset)); 2897 __ mov(ecx, Operand(ebx, ArgumentsAdaptorFrameConstants::kLengthOffset));
2898 __ cmp(edx, Operand(ecx)); 2898 __ cmp(edx, Operand(ecx));
2899 __ j(above_equal, &slow); 2899 __ j(above_equal, &slow, Label::kNear);
2900 2900
2901 // Read the argument from the stack and return it. 2901 // Read the argument from the stack and return it.
2902 STATIC_ASSERT(kSmiTagSize == 1); 2902 STATIC_ASSERT(kSmiTagSize == 1);
2903 STATIC_ASSERT(kSmiTag == 0); // Shifting code depends on these. 2903 STATIC_ASSERT(kSmiTag == 0); // Shifting code depends on these.
2904 __ lea(ebx, Operand(ebx, ecx, times_2, 0)); 2904 __ lea(ebx, Operand(ebx, ecx, times_2, 0));
2905 __ neg(edx); 2905 __ neg(edx);
2906 __ mov(eax, Operand(ebx, edx, times_2, kDisplacement)); 2906 __ mov(eax, Operand(ebx, edx, times_2, kDisplacement));
2907 __ ret(0); 2907 __ ret(0);
2908 2908
2909 // Slow-case: Handle non-smi or out-of-bounds access to arguments 2909 // Slow-case: Handle non-smi or out-of-bounds access to arguments
(...skipping 258 matching lines...) Expand 10 before | Expand all | Expand 10 after
3168 // esp[0] : return address 3168 // esp[0] : return address
3169 // esp[4] : number of parameters 3169 // esp[4] : number of parameters
3170 // esp[8] : receiver displacement 3170 // esp[8] : receiver displacement
3171 // esp[12] : function 3171 // esp[12] : function
3172 3172
3173 // Check if the calling frame is an arguments adaptor frame. 3173 // Check if the calling frame is an arguments adaptor frame.
3174 Label adaptor_frame, try_allocate, runtime; 3174 Label adaptor_frame, try_allocate, runtime;
3175 __ mov(edx, Operand(ebp, StandardFrameConstants::kCallerFPOffset)); 3175 __ mov(edx, Operand(ebp, StandardFrameConstants::kCallerFPOffset));
3176 __ mov(ecx, Operand(edx, StandardFrameConstants::kContextOffset)); 3176 __ mov(ecx, Operand(edx, StandardFrameConstants::kContextOffset));
3177 __ cmp(Operand(ecx), Immediate(Smi::FromInt(StackFrame::ARGUMENTS_ADAPTOR))); 3177 __ cmp(Operand(ecx), Immediate(Smi::FromInt(StackFrame::ARGUMENTS_ADAPTOR)));
3178 __ j(equal, &adaptor_frame); 3178 __ j(equal, &adaptor_frame, Label::kNear);
3179 3179
3180 // Get the length from the frame. 3180 // Get the length from the frame.
3181 __ mov(ecx, Operand(esp, 1 * kPointerSize)); 3181 __ mov(ecx, Operand(esp, 1 * kPointerSize));
3182 __ jmp(&try_allocate); 3182 __ jmp(&try_allocate, Label::kNear);
3183 3183
3184 // Patch the arguments.length and the parameters pointer. 3184 // Patch the arguments.length and the parameters pointer.
3185 __ bind(&adaptor_frame); 3185 __ bind(&adaptor_frame);
3186 __ mov(ecx, Operand(edx, ArgumentsAdaptorFrameConstants::kLengthOffset)); 3186 __ mov(ecx, Operand(edx, ArgumentsAdaptorFrameConstants::kLengthOffset));
3187 __ mov(Operand(esp, 1 * kPointerSize), ecx); 3187 __ mov(Operand(esp, 1 * kPointerSize), ecx);
3188 __ lea(edx, Operand(edx, ecx, times_2, 3188 __ lea(edx, Operand(edx, ecx, times_2,
3189 StandardFrameConstants::kCallerSPOffset)); 3189 StandardFrameConstants::kCallerSPOffset));
3190 __ mov(Operand(esp, 2 * kPointerSize), edx); 3190 __ mov(Operand(esp, 2 * kPointerSize), edx);
3191 3191
3192 // Try the new space allocation. Start out with computing the size of 3192 // Try the new space allocation. Start out with computing the size of
(...skipping 25 matching lines...) Expand all
3218 // Get the length (smi tagged) and set that as an in-object property too. 3218 // Get the length (smi tagged) and set that as an in-object property too.
3219 STATIC_ASSERT(Heap::kArgumentsLengthIndex == 0); 3219 STATIC_ASSERT(Heap::kArgumentsLengthIndex == 0);
3220 __ mov(ecx, Operand(esp, 1 * kPointerSize)); 3220 __ mov(ecx, Operand(esp, 1 * kPointerSize));
3221 __ mov(FieldOperand(eax, JSObject::kHeaderSize + 3221 __ mov(FieldOperand(eax, JSObject::kHeaderSize +
3222 Heap::kArgumentsLengthIndex * kPointerSize), 3222 Heap::kArgumentsLengthIndex * kPointerSize),
3223 ecx); 3223 ecx);
3224 3224
3225 // If there are no actual arguments, we're done. 3225 // If there are no actual arguments, we're done.
3226 Label done; 3226 Label done;
3227 __ test(ecx, Operand(ecx)); 3227 __ test(ecx, Operand(ecx));
3228 __ j(zero, &done); 3228 __ j(zero, &done, Label::kNear);
3229 3229
3230 // Get the parameters pointer from the stack. 3230 // Get the parameters pointer from the stack.
3231 __ mov(edx, Operand(esp, 2 * kPointerSize)); 3231 __ mov(edx, Operand(esp, 2 * kPointerSize));
3232 3232
3233 // Setup the elements pointer in the allocated arguments object and 3233 // Setup the elements pointer in the allocated arguments object and
3234 // initialize the header in the elements fixed array. 3234 // initialize the header in the elements fixed array.
3235 __ lea(edi, Operand(eax, Heap::kArgumentsObjectSizeStrict)); 3235 __ lea(edi, Operand(eax, Heap::kArgumentsObjectSizeStrict));
3236 __ mov(FieldOperand(eax, JSObject::kElementsOffset), edi); 3236 __ mov(FieldOperand(eax, JSObject::kElementsOffset), edi);
3237 __ mov(FieldOperand(edi, FixedArray::kMapOffset), 3237 __ mov(FieldOperand(edi, FixedArray::kMapOffset),
3238 Immediate(FACTORY->fixed_array_map())); 3238 Immediate(FACTORY->fixed_array_map()));
(...skipping 576 matching lines...) Expand 10 before | Expand all | Expand 10 after
3815 static int NegativeComparisonResult(Condition cc) { 3815 static int NegativeComparisonResult(Condition cc) {
3816 ASSERT(cc != equal); 3816 ASSERT(cc != equal);
3817 ASSERT((cc == less) || (cc == less_equal) 3817 ASSERT((cc == less) || (cc == less_equal)
3818 || (cc == greater) || (cc == greater_equal)); 3818 || (cc == greater) || (cc == greater_equal));
3819 return (cc == greater || cc == greater_equal) ? LESS : GREATER; 3819 return (cc == greater || cc == greater_equal) ? LESS : GREATER;
3820 } 3820 }
3821 3821
3822 void CompareStub::Generate(MacroAssembler* masm) { 3822 void CompareStub::Generate(MacroAssembler* masm) {
3823 ASSERT(lhs_.is(no_reg) && rhs_.is(no_reg)); 3823 ASSERT(lhs_.is(no_reg) && rhs_.is(no_reg));
3824 3824
3825 Label check_unequal_objects, done; 3825 Label check_unequal_objects;
3826 3826
3827 // Compare two smis if required. 3827 // Compare two smis if required.
3828 if (include_smi_compare_) { 3828 if (include_smi_compare_) {
3829 Label non_smi, smi_done; 3829 Label non_smi, smi_done;
3830 __ mov(ecx, Operand(edx)); 3830 __ mov(ecx, Operand(edx));
3831 __ or_(ecx, Operand(eax)); 3831 __ or_(ecx, Operand(eax));
3832 __ JumpIfNotSmi(ecx, &non_smi); 3832 __ JumpIfNotSmi(ecx, &non_smi, Label::kNear);
3833 __ sub(edx, Operand(eax)); // Return on the result of the subtraction. 3833 __ sub(edx, Operand(eax)); // Return on the result of the subtraction.
3834 __ j(no_overflow, &smi_done); 3834 __ j(no_overflow, &smi_done, Label::kNear);
3835 __ not_(edx); // Correct sign in case of overflow. edx is never 0 here. 3835 __ not_(edx); // Correct sign in case of overflow. edx is never 0 here.
3836 __ bind(&smi_done); 3836 __ bind(&smi_done);
3837 __ mov(eax, edx); 3837 __ mov(eax, edx);
3838 __ ret(0); 3838 __ ret(0);
3839 __ bind(&non_smi); 3839 __ bind(&non_smi);
3840 } else if (FLAG_debug_code) { 3840 } else if (FLAG_debug_code) {
3841 __ mov(ecx, Operand(edx)); 3841 __ mov(ecx, Operand(edx));
3842 __ or_(ecx, Operand(eax)); 3842 __ or_(ecx, Operand(eax));
3843 __ test(ecx, Immediate(kSmiTagMask)); 3843 __ test(ecx, Immediate(kSmiTagMask));
3844 __ Assert(not_zero, "Unexpected smi operands."); 3844 __ Assert(not_zero, "Unexpected smi operands.");
(...skipping 101 matching lines...) Expand 10 before | Expand all | Expand 10 after
3946 __ mov(ebx, edx); 3946 __ mov(ebx, edx);
3947 __ xor_(ebx, Operand(eax)); 3947 __ xor_(ebx, Operand(eax));
3948 __ and_(ebx, Operand(ecx)); // ebx holds either 0 or eax ^ edx. 3948 __ and_(ebx, Operand(ecx)); // ebx holds either 0 or eax ^ edx.
3949 __ xor_(ebx, Operand(eax)); 3949 __ xor_(ebx, Operand(eax));
3950 // if eax was smi, ebx is now edx, else eax. 3950 // if eax was smi, ebx is now edx, else eax.
3951 3951
3952 // Check if the non-smi operand is a heap number. 3952 // Check if the non-smi operand is a heap number.
3953 __ cmp(FieldOperand(ebx, HeapObject::kMapOffset), 3953 __ cmp(FieldOperand(ebx, HeapObject::kMapOffset),
3954 Immediate(masm->isolate()->factory()->heap_number_map())); 3954 Immediate(masm->isolate()->factory()->heap_number_map()));
3955 // If heap number, handle it in the slow case. 3955 // If heap number, handle it in the slow case.
3956 __ j(equal, &slow); 3956 __ j(equal, &slow, Label::kNear);
3957 // Return non-equal (ebx is not zero) 3957 // Return non-equal (ebx is not zero)
3958 __ mov(eax, ebx); 3958 __ mov(eax, ebx);
3959 __ ret(0); 3959 __ ret(0);
3960 3960
3961 __ bind(&not_smis); 3961 __ bind(&not_smis);
3962 // If either operand is a JSObject or an oddball value, then they are not 3962 // If either operand is a JSObject or an oddball value, then they are not
3963 // equal since their pointers are different 3963 // equal since their pointers are different
3964 // There is no test for undetectability in strict equality. 3964 // There is no test for undetectability in strict equality.
3965 3965
3966 // Get the type of the first operand. 3966 // Get the type of the first operand.
(...skipping 30 matching lines...) Expand all
3997 Label non_number_comparison; 3997 Label non_number_comparison;
3998 Label unordered; 3998 Label unordered;
3999 if (CpuFeatures::IsSupported(SSE2)) { 3999 if (CpuFeatures::IsSupported(SSE2)) {
4000 CpuFeatures::Scope use_sse2(SSE2); 4000 CpuFeatures::Scope use_sse2(SSE2);
4001 CpuFeatures::Scope use_cmov(CMOV); 4001 CpuFeatures::Scope use_cmov(CMOV);
4002 4002
4003 FloatingPointHelper::LoadSSE2Operands(masm, &non_number_comparison); 4003 FloatingPointHelper::LoadSSE2Operands(masm, &non_number_comparison);
4004 __ ucomisd(xmm0, xmm1); 4004 __ ucomisd(xmm0, xmm1);
4005 4005
4006 // Don't base result on EFLAGS when a NaN is involved. 4006 // Don't base result on EFLAGS when a NaN is involved.
4007 __ j(parity_even, &unordered); 4007 __ j(parity_even, &unordered, Label::kNear);
4008 // Return a result of -1, 0, or 1, based on EFLAGS. 4008 // Return a result of -1, 0, or 1, based on EFLAGS.
4009 __ mov(eax, 0); // equal 4009 __ mov(eax, 0); // equal
4010 __ mov(ecx, Immediate(Smi::FromInt(1))); 4010 __ mov(ecx, Immediate(Smi::FromInt(1)));
4011 __ cmov(above, eax, Operand(ecx)); 4011 __ cmov(above, eax, Operand(ecx));
4012 __ mov(ecx, Immediate(Smi::FromInt(-1))); 4012 __ mov(ecx, Immediate(Smi::FromInt(-1)));
4013 __ cmov(below, eax, Operand(ecx)); 4013 __ cmov(below, eax, Operand(ecx));
4014 __ ret(0); 4014 __ ret(0);
4015 } else { 4015 } else {
4016 FloatingPointHelper::CheckFloatOperands( 4016 FloatingPointHelper::CheckFloatOperands(
4017 masm, &non_number_comparison, ebx); 4017 masm, &non_number_comparison, ebx);
4018 FloatingPointHelper::LoadFloatOperand(masm, eax); 4018 FloatingPointHelper::LoadFloatOperand(masm, eax);
4019 FloatingPointHelper::LoadFloatOperand(masm, edx); 4019 FloatingPointHelper::LoadFloatOperand(masm, edx);
4020 __ FCmp(); 4020 __ FCmp();
4021 4021
4022 // Don't base result on EFLAGS when a NaN is involved. 4022 // Don't base result on EFLAGS when a NaN is involved.
4023 __ j(parity_even, &unordered); 4023 __ j(parity_even, &unordered, Label::kNear);
4024 4024
4025 Label below_label, above_label; 4025 Label below_label, above_label;
4026 // Return a result of -1, 0, or 1, based on EFLAGS. 4026 // Return a result of -1, 0, or 1, based on EFLAGS.
4027 __ j(below, &below_label); 4027 __ j(below, &below_label, Label::kNear);
4028 __ j(above, &above_label); 4028 __ j(above, &above_label, Label::kNear);
4029 4029
4030 __ Set(eax, Immediate(0)); 4030 __ Set(eax, Immediate(0));
4031 __ ret(0); 4031 __ ret(0);
4032 4032
4033 __ bind(&below_label); 4033 __ bind(&below_label);
4034 __ mov(eax, Immediate(Smi::FromInt(-1))); 4034 __ mov(eax, Immediate(Smi::FromInt(-1)));
4035 __ ret(0); 4035 __ ret(0);
4036 4036
4037 __ bind(&above_label); 4037 __ bind(&above_label);
4038 __ mov(eax, Immediate(Smi::FromInt(1))); 4038 __ mov(eax, Immediate(Smi::FromInt(1)));
(...skipping 294 matching lines...) Expand 10 before | Expand all | Expand 10 after
4333 __ LeaveExitFrame(save_doubles_); 4333 __ LeaveExitFrame(save_doubles_);
4334 __ ret(0); 4334 __ ret(0);
4335 4335
4336 // Handling of failure. 4336 // Handling of failure.
4337 __ bind(&failure_returned); 4337 __ bind(&failure_returned);
4338 4338
4339 Label retry; 4339 Label retry;
4340 // If the returned exception is RETRY_AFTER_GC continue at retry label 4340 // If the returned exception is RETRY_AFTER_GC continue at retry label
4341 STATIC_ASSERT(Failure::RETRY_AFTER_GC == 0); 4341 STATIC_ASSERT(Failure::RETRY_AFTER_GC == 0);
4342 __ test(eax, Immediate(((1 << kFailureTypeTagSize) - 1) << kFailureTagSize)); 4342 __ test(eax, Immediate(((1 << kFailureTypeTagSize) - 1) << kFailureTagSize));
4343 __ j(zero, &retry); 4343 __ j(zero, &retry, Label::kNear);
4344 4344
4345 // Special handling of out of memory exceptions. 4345 // Special handling of out of memory exceptions.
4346 __ cmp(eax, reinterpret_cast<int32_t>(Failure::OutOfMemoryException())); 4346 __ cmp(eax, reinterpret_cast<int32_t>(Failure::OutOfMemoryException()));
4347 __ j(equal, throw_out_of_memory_exception); 4347 __ j(equal, throw_out_of_memory_exception);
4348 4348
4349 // Retrieve the pending exception and clear the variable. 4349 // Retrieve the pending exception and clear the variable.
4350 ExternalReference the_hole_location = 4350 ExternalReference the_hole_location =
4351 ExternalReference::the_hole_value_location(masm->isolate()); 4351 ExternalReference::the_hole_value_location(masm->isolate());
4352 __ mov(eax, Operand::StaticVariable(pending_exception_address)); 4352 __ mov(eax, Operand::StaticVariable(pending_exception_address));
4353 __ mov(edx, Operand::StaticVariable(the_hole_location)); 4353 __ mov(edx, Operand::StaticVariable(the_hole_location));
(...skipping 99 matching lines...) Expand 10 before | Expand all | Expand 10 after
4453 __ push(ebx); 4453 __ push(ebx);
4454 4454
4455 // Save copies of the top frame descriptor on the stack. 4455 // Save copies of the top frame descriptor on the stack.
4456 ExternalReference c_entry_fp(Isolate::k_c_entry_fp_address, masm->isolate()); 4456 ExternalReference c_entry_fp(Isolate::k_c_entry_fp_address, masm->isolate());
4457 __ push(Operand::StaticVariable(c_entry_fp)); 4457 __ push(Operand::StaticVariable(c_entry_fp));
4458 4458
4459 // If this is the outermost JS call, set js_entry_sp value. 4459 // If this is the outermost JS call, set js_entry_sp value.
4460 ExternalReference js_entry_sp(Isolate::k_js_entry_sp_address, 4460 ExternalReference js_entry_sp(Isolate::k_js_entry_sp_address,
4461 masm->isolate()); 4461 masm->isolate());
4462 __ cmp(Operand::StaticVariable(js_entry_sp), Immediate(0)); 4462 __ cmp(Operand::StaticVariable(js_entry_sp), Immediate(0));
4463 __ j(not_equal, &not_outermost_js); 4463 __ j(not_equal, &not_outermost_js, Label::kNear);
4464 __ mov(Operand::StaticVariable(js_entry_sp), ebp); 4464 __ mov(Operand::StaticVariable(js_entry_sp), ebp);
4465 __ push(Immediate(Smi::FromInt(StackFrame::OUTERMOST_JSENTRY_FRAME))); 4465 __ push(Immediate(Smi::FromInt(StackFrame::OUTERMOST_JSENTRY_FRAME)));
4466 Label cont; 4466 Label cont;
4467 __ jmp(&cont); 4467 __ jmp(&cont, Label::kNear);
4468 __ bind(&not_outermost_js); 4468 __ bind(&not_outermost_js);
4469 __ push(Immediate(Smi::FromInt(StackFrame::INNER_JSENTRY_FRAME))); 4469 __ push(Immediate(Smi::FromInt(StackFrame::INNER_JSENTRY_FRAME)));
4470 __ bind(&cont); 4470 __ bind(&cont);
4471 4471
4472 // Call a faked try-block that does the invoke. 4472 // Call a faked try-block that does the invoke.
4473 __ call(&invoke); 4473 __ call(&invoke);
4474 4474
4475 // Caught exception: Store result (exception) in the pending 4475 // Caught exception: Store result (exception) in the pending
4476 // exception field in the JSEnv and return a failure sentinel. 4476 // exception field in the JSEnv and return a failure sentinel.
4477 ExternalReference pending_exception(Isolate::k_pending_exception_address, 4477 ExternalReference pending_exception(Isolate::k_pending_exception_address,
(...skipping 220 matching lines...) Expand 10 before | Expand all | Expand 10 after
4698 if (!ReturnTrueFalseObject()) { 4698 if (!ReturnTrueFalseObject()) {
4699 __ Set(eax, Immediate(Smi::FromInt(1))); 4699 __ Set(eax, Immediate(Smi::FromInt(1)));
4700 } 4700 }
4701 } 4701 }
4702 __ ret((HasArgsInRegisters() ? 0 : 2) * kPointerSize); 4702 __ ret((HasArgsInRegisters() ? 0 : 2) * kPointerSize);
4703 4703
4704 Label object_not_null, object_not_null_or_smi; 4704 Label object_not_null, object_not_null_or_smi;
4705 __ bind(&not_js_object); 4705 __ bind(&not_js_object);
4706 // Before null, smi and string value checks, check that the rhs is a function 4706 // Before null, smi and string value checks, check that the rhs is a function
4707 // as for a non-function rhs an exception needs to be thrown. 4707 // as for a non-function rhs an exception needs to be thrown.
4708 __ JumpIfSmi(function, &slow); 4708 __ JumpIfSmi(function, &slow, Label::kNear);
4709 __ CmpObjectType(function, JS_FUNCTION_TYPE, scratch); 4709 __ CmpObjectType(function, JS_FUNCTION_TYPE, scratch);
4710 __ j(not_equal, &slow); 4710 __ j(not_equal, &slow, Label::kNear);
4711 4711
4712 // Null is not instance of anything. 4712 // Null is not instance of anything.
4713 __ cmp(object, factory->null_value()); 4713 __ cmp(object, factory->null_value());
4714 __ j(not_equal, &object_not_null); 4714 __ j(not_equal, &object_not_null, Label::kNear);
4715 __ Set(eax, Immediate(Smi::FromInt(1))); 4715 __ Set(eax, Immediate(Smi::FromInt(1)));
4716 __ ret((HasArgsInRegisters() ? 0 : 2) * kPointerSize); 4716 __ ret((HasArgsInRegisters() ? 0 : 2) * kPointerSize);
4717 4717
4718 __ bind(&object_not_null); 4718 __ bind(&object_not_null);
4719 // Smi values is not instance of anything. 4719 // Smi values is not instance of anything.
4720 __ JumpIfNotSmi(object, &object_not_null_or_smi); 4720 __ JumpIfNotSmi(object, &object_not_null_or_smi, Label::kNear);
4721 __ Set(eax, Immediate(Smi::FromInt(1))); 4721 __ Set(eax, Immediate(Smi::FromInt(1)));
4722 __ ret((HasArgsInRegisters() ? 0 : 2) * kPointerSize); 4722 __ ret((HasArgsInRegisters() ? 0 : 2) * kPointerSize);
4723 4723
4724 __ bind(&object_not_null_or_smi); 4724 __ bind(&object_not_null_or_smi);
4725 // String values is not instance of anything. 4725 // String values is not instance of anything.
4726 Condition is_string = masm->IsObjectStringType(object, scratch, scratch); 4726 Condition is_string = masm->IsObjectStringType(object, scratch, scratch);
4727 __ j(NegateCondition(is_string), &slow); 4727 __ j(NegateCondition(is_string), &slow, Label::kNear);
4728 __ Set(eax, Immediate(Smi::FromInt(1))); 4728 __ Set(eax, Immediate(Smi::FromInt(1)));
4729 __ ret((HasArgsInRegisters() ? 0 : 2) * kPointerSize); 4729 __ ret((HasArgsInRegisters() ? 0 : 2) * kPointerSize);
4730 4730
4731 // Slow-case: Go through the JavaScript implementation. 4731 // Slow-case: Go through the JavaScript implementation.
4732 __ bind(&slow); 4732 __ bind(&slow);
4733 if (!ReturnTrueFalseObject()) { 4733 if (!ReturnTrueFalseObject()) {
4734 // Tail call the builtin which returns 0 or 1. 4734 // Tail call the builtin which returns 0 or 1.
4735 if (HasArgsInRegisters()) { 4735 if (HasArgsInRegisters()) {
4736 // Push arguments below return address. 4736 // Push arguments below return address.
4737 __ pop(scratch); 4737 __ pop(scratch);
(...skipping 1627 matching lines...) Expand 10 before | Expand all | Expand 10 after
6365 __ Drop(1); 6365 __ Drop(1);
6366 __ ret(2 * kPointerSize); 6366 __ ret(2 * kPointerSize);
6367 } 6367 }
6368 6368
6369 6369
6370 #undef __ 6370 #undef __
6371 6371
6372 } } // namespace v8::internal 6372 } } // namespace v8::internal
6373 6373
6374 #endif // V8_TARGET_ARCH_IA32 6374 #endif // V8_TARGET_ARCH_IA32
OLDNEW
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698