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

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

Issue 1927003003: Version 5.0.71.40 (cherry-pick) (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@5.0
Patch Set: Created 4 years, 7 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
« no previous file with comments | « src/ppc/code-stubs-ppc.cc ('k') | src/x87/code-stubs-x87.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2013 the V8 project authors. All rights reserved. 1 // Copyright 2013 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #if V8_TARGET_ARCH_X64 5 #if V8_TARGET_ARCH_X64
6 6
7 #include "src/bootstrapper.h" 7 #include "src/bootstrapper.h"
8 #include "src/code-stubs.h" 8 #include "src/code-stubs.h"
9 #include "src/codegen.h" 9 #include "src/codegen.h"
10 #include "src/ic/handler-compiler.h" 10 #include "src/ic/handler-compiler.h"
(...skipping 649 matching lines...) Expand 10 before | Expand all | Expand 10 after
660 // Or number_of_captures <= offsets vector size / 2 - 1 660 // Or number_of_captures <= offsets vector size / 2 - 1
661 STATIC_ASSERT(Isolate::kJSRegexpStaticOffsetsVectorSize >= 2); 661 STATIC_ASSERT(Isolate::kJSRegexpStaticOffsetsVectorSize >= 2);
662 __ cmpl(rdx, Immediate(Isolate::kJSRegexpStaticOffsetsVectorSize / 2 - 1)); 662 __ cmpl(rdx, Immediate(Isolate::kJSRegexpStaticOffsetsVectorSize / 2 - 1));
663 __ j(above, &runtime); 663 __ j(above, &runtime);
664 664
665 // Reset offset for possibly sliced string. 665 // Reset offset for possibly sliced string.
666 __ Set(r14, 0); 666 __ Set(r14, 0);
667 __ movp(rdi, args.GetArgumentOperand(SUBJECT_STRING_ARGUMENT_INDEX)); 667 __ movp(rdi, args.GetArgumentOperand(SUBJECT_STRING_ARGUMENT_INDEX));
668 __ JumpIfSmi(rdi, &runtime); 668 __ JumpIfSmi(rdi, &runtime);
669 __ movp(r15, rdi); // Make a copy of the original subject string. 669 __ movp(r15, rdi); // Make a copy of the original subject string.
670 __ movp(rbx, FieldOperand(rdi, HeapObject::kMapOffset));
671 __ movzxbl(rbx, FieldOperand(rbx, Map::kInstanceTypeOffset));
672 // rax: RegExp data (FixedArray) 670 // rax: RegExp data (FixedArray)
673 // rdi: subject string 671 // rdi: subject string
674 // r15: subject string 672 // r15: subject string
675 // Handle subject string according to its encoding and representation: 673 // Handle subject string according to its encoding and representation:
676 // (1) Sequential two byte? If yes, go to (9). 674 // (1) Sequential two byte? If yes, go to (9).
677 // (2) Sequential one byte? If yes, go to (6). 675 // (2) Sequential one byte? If yes, go to (5).
678 // (3) Anything but sequential or cons? If yes, go to (7). 676 // (3) Sequential or cons? If not, go to (6).
679 // (4) Cons string. If the string is flat, replace subject with first string. 677 // (4) Cons string. If the string is flat, replace subject with first string
680 // Otherwise bailout. 678 // and go to (1). Otherwise bail out to runtime.
681 // (5a) Is subject sequential two byte? If yes, go to (9). 679 // (5) One byte sequential. Load regexp code for one byte.
682 // (5b) Is subject external? If yes, go to (8).
683 // (6) One byte sequential. Load regexp code for one byte.
684 // (E) Carry on. 680 // (E) Carry on.
685 /// [...] 681 /// [...]
686 682
687 // Deferred code at the end of the stub: 683 // Deferred code at the end of the stub:
688 // (7) Not a long external string? If yes, go to (10). 684 // (6) Long external string? If not, go to (10).
689 // (8) External string. Make it, offset-wise, look like a sequential string. 685 // (7) External string. Make it, offset-wise, look like a sequential string.
690 // (8a) Is the external string one byte? If yes, go to (6). 686 // (8) Is the external string one byte? If yes, go to (5).
691 // (9) Two byte sequential. Load regexp code for one byte. Go to (E). 687 // (9) Two byte sequential. Load regexp code for two byte. Go to (E).
692 // (10) Short external string or not a string? If yes, bail out to runtime. 688 // (10) Short external string or not a string? If yes, bail out to runtime.
693 // (11) Sliced string. Replace subject with parent. Go to (5a). 689 // (11) Sliced string. Replace subject with parent. Go to (1).
694 690
695 Label seq_one_byte_string /* 6 */, seq_two_byte_string /* 9 */, 691 Label seq_one_byte_string /* 5 */, seq_two_byte_string /* 9 */,
696 external_string /* 8 */, check_underlying /* 5a */, 692 external_string /* 7 */, check_underlying /* 1 */,
697 not_seq_nor_cons /* 7 */, check_code /* E */, 693 not_seq_nor_cons /* 6 */, check_code /* E */, not_long_external /* 10 */;
698 not_long_external /* 10 */; 694
695 __ bind(&check_underlying);
696 __ movp(rbx, FieldOperand(rdi, HeapObject::kMapOffset));
697 __ movzxbl(rbx, FieldOperand(rbx, Map::kInstanceTypeOffset));
699 698
700 // (1) Sequential two byte? If yes, go to (9). 699 // (1) Sequential two byte? If yes, go to (9).
701 __ andb(rbx, Immediate(kIsNotStringMask | 700 __ andb(rbx, Immediate(kIsNotStringMask |
702 kStringRepresentationMask | 701 kStringRepresentationMask |
703 kStringEncodingMask | 702 kStringEncodingMask |
704 kShortExternalStringMask)); 703 kShortExternalStringMask));
705 STATIC_ASSERT((kStringTag | kSeqStringTag | kTwoByteStringTag) == 0); 704 STATIC_ASSERT((kStringTag | kSeqStringTag | kTwoByteStringTag) == 0);
706 __ j(zero, &seq_two_byte_string); // Go to (9). 705 __ j(zero, &seq_two_byte_string); // Go to (9).
707 706
708 // (2) Sequential one byte? If yes, go to (6). 707 // (2) Sequential one byte? If yes, go to (5).
709 // Any other sequential string must be one byte. 708 // Any other sequential string must be one byte.
710 __ andb(rbx, Immediate(kIsNotStringMask | 709 __ andb(rbx, Immediate(kIsNotStringMask |
711 kStringRepresentationMask | 710 kStringRepresentationMask |
712 kShortExternalStringMask)); 711 kShortExternalStringMask));
713 __ j(zero, &seq_one_byte_string, Label::kNear); // Go to (6). 712 __ j(zero, &seq_one_byte_string, Label::kNear); // Go to (5).
714 713
715 // (3) Anything but sequential or cons? If yes, go to (7). 714 // (3) Sequential or cons? If not, go to (6).
716 // We check whether the subject string is a cons, since sequential strings 715 // We check whether the subject string is a cons, since sequential strings
717 // have already been covered. 716 // have already been covered.
718 STATIC_ASSERT(kConsStringTag < kExternalStringTag); 717 STATIC_ASSERT(kConsStringTag < kExternalStringTag);
719 STATIC_ASSERT(kSlicedStringTag > kExternalStringTag); 718 STATIC_ASSERT(kSlicedStringTag > kExternalStringTag);
720 STATIC_ASSERT(kIsNotStringMask > kExternalStringTag); 719 STATIC_ASSERT(kIsNotStringMask > kExternalStringTag);
721 STATIC_ASSERT(kShortExternalStringTag > kExternalStringTag); 720 STATIC_ASSERT(kShortExternalStringTag > kExternalStringTag);
722 __ cmpp(rbx, Immediate(kExternalStringTag)); 721 __ cmpp(rbx, Immediate(kExternalStringTag));
723 __ j(greater_equal, &not_seq_nor_cons); // Go to (7). 722 __ j(greater_equal, &not_seq_nor_cons); // Go to (6).
724 723
725 // (4) Cons string. Check that it's flat. 724 // (4) Cons string. Check that it's flat.
726 // Replace subject with first string and reload instance type. 725 // Replace subject with first string and reload instance type.
727 __ CompareRoot(FieldOperand(rdi, ConsString::kSecondOffset), 726 __ CompareRoot(FieldOperand(rdi, ConsString::kSecondOffset),
728 Heap::kempty_stringRootIndex); 727 Heap::kempty_stringRootIndex);
729 __ j(not_equal, &runtime); 728 __ j(not_equal, &runtime);
730 __ movp(rdi, FieldOperand(rdi, ConsString::kFirstOffset)); 729 __ movp(rdi, FieldOperand(rdi, ConsString::kFirstOffset));
731 __ bind(&check_underlying); 730 __ jmp(&check_underlying);
732 __ movp(rbx, FieldOperand(rdi, HeapObject::kMapOffset));
733 __ movp(rbx, FieldOperand(rbx, Map::kInstanceTypeOffset));
734 731
735 // (5a) Is subject sequential two byte? If yes, go to (9). 732 // (5) One byte sequential. Load regexp code for one byte.
736 __ testb(rbx, Immediate(kStringRepresentationMask | kStringEncodingMask));
737 STATIC_ASSERT((kSeqStringTag | kTwoByteStringTag) == 0);
738 __ j(zero, &seq_two_byte_string); // Go to (9).
739 // (5b) Is subject external? If yes, go to (8).
740 __ testb(rbx, Immediate(kStringRepresentationMask));
741 // The underlying external string is never a short external string.
742 STATIC_ASSERT(ExternalString::kMaxShortLength < ConsString::kMinLength);
743 STATIC_ASSERT(ExternalString::kMaxShortLength < SlicedString::kMinLength);
744 __ j(not_zero, &external_string); // Go to (8)
745
746 // (6) One byte sequential. Load regexp code for one byte.
747 __ bind(&seq_one_byte_string); 733 __ bind(&seq_one_byte_string);
748 // rax: RegExp data (FixedArray) 734 // rax: RegExp data (FixedArray)
749 __ movp(r11, FieldOperand(rax, JSRegExp::kDataOneByteCodeOffset)); 735 __ movp(r11, FieldOperand(rax, JSRegExp::kDataOneByteCodeOffset));
750 __ Set(rcx, 1); // Type is one byte. 736 __ Set(rcx, 1); // Type is one byte.
751 737
752 // (E) Carry on. String handling is done. 738 // (E) Carry on. String handling is done.
753 __ bind(&check_code); 739 __ bind(&check_code);
754 // r11: irregexp code 740 // r11: irregexp code
755 // Check that the irregexp code has been generated for the actual string 741 // Check that the irregexp code has been generated for the actual string
756 // encoding. If it has, the field contains a code object otherwise it contains 742 // encoding. If it has, the field contains a code object otherwise it contains
(...skipping 226 matching lines...) Expand 10 before | Expand all | Expand 10 after
983 __ j(equal, &runtime); 969 __ j(equal, &runtime);
984 970
985 // For exception, throw the exception again. 971 // For exception, throw the exception again.
986 __ TailCallRuntime(Runtime::kRegExpExecReThrow); 972 __ TailCallRuntime(Runtime::kRegExpExecReThrow);
987 973
988 // Do the runtime call to execute the regexp. 974 // Do the runtime call to execute the regexp.
989 __ bind(&runtime); 975 __ bind(&runtime);
990 __ TailCallRuntime(Runtime::kRegExpExec); 976 __ TailCallRuntime(Runtime::kRegExpExec);
991 977
992 // Deferred code for string handling. 978 // Deferred code for string handling.
993 // (7) Not a long external string? If yes, go to (10). 979 // (6) Long external string? If not, go to (10).
994 __ bind(&not_seq_nor_cons); 980 __ bind(&not_seq_nor_cons);
995 // Compare flags are still set from (3). 981 // Compare flags are still set from (3).
996 __ j(greater, &not_long_external, Label::kNear); // Go to (10). 982 __ j(greater, &not_long_external, Label::kNear); // Go to (10).
997 983
998 // (8) External string. Short external strings have been ruled out. 984 // (7) External string. Short external strings have been ruled out.
999 __ bind(&external_string); 985 __ bind(&external_string);
1000 __ movp(rbx, FieldOperand(rdi, HeapObject::kMapOffset)); 986 __ movp(rbx, FieldOperand(rdi, HeapObject::kMapOffset));
1001 __ movzxbl(rbx, FieldOperand(rbx, Map::kInstanceTypeOffset)); 987 __ movzxbl(rbx, FieldOperand(rbx, Map::kInstanceTypeOffset));
1002 if (FLAG_debug_code) { 988 if (FLAG_debug_code) {
1003 // Assert that we do not have a cons or slice (indirect strings) here. 989 // Assert that we do not have a cons or slice (indirect strings) here.
1004 // Sequential strings have already been ruled out. 990 // Sequential strings have already been ruled out.
1005 __ testb(rbx, Immediate(kIsIndirectStringMask)); 991 __ testb(rbx, Immediate(kIsIndirectStringMask));
1006 __ Assert(zero, kExternalStringExpectedButNotFound); 992 __ Assert(zero, kExternalStringExpectedButNotFound);
1007 } 993 }
1008 __ movp(rdi, FieldOperand(rdi, ExternalString::kResourceDataOffset)); 994 __ movp(rdi, FieldOperand(rdi, ExternalString::kResourceDataOffset));
1009 // Move the pointer so that offset-wise, it looks like a sequential string. 995 // Move the pointer so that offset-wise, it looks like a sequential string.
1010 STATIC_ASSERT(SeqTwoByteString::kHeaderSize == SeqOneByteString::kHeaderSize); 996 STATIC_ASSERT(SeqTwoByteString::kHeaderSize == SeqOneByteString::kHeaderSize);
1011 __ subp(rdi, Immediate(SeqTwoByteString::kHeaderSize - kHeapObjectTag)); 997 __ subp(rdi, Immediate(SeqTwoByteString::kHeaderSize - kHeapObjectTag));
1012 STATIC_ASSERT(kTwoByteStringTag == 0); 998 STATIC_ASSERT(kTwoByteStringTag == 0);
1013 // (8a) Is the external string one byte? If yes, go to (6). 999 // (8) Is the external string one byte? If yes, go to (5).
1014 __ testb(rbx, Immediate(kStringEncodingMask)); 1000 __ testb(rbx, Immediate(kStringEncodingMask));
1015 __ j(not_zero, &seq_one_byte_string); // Goto (6). 1001 __ j(not_zero, &seq_one_byte_string); // Go to (5).
1016 1002
1017 // rdi: subject string (flat two-byte) 1003 // rdi: subject string (flat two-byte)
1018 // rax: RegExp data (FixedArray) 1004 // rax: RegExp data (FixedArray)
1019 // (9) Two byte sequential. Load regexp code for one byte. Go to (E). 1005 // (9) Two byte sequential. Load regexp code for two byte. Go to (E).
1020 __ bind(&seq_two_byte_string); 1006 __ bind(&seq_two_byte_string);
1021 __ movp(r11, FieldOperand(rax, JSRegExp::kDataUC16CodeOffset)); 1007 __ movp(r11, FieldOperand(rax, JSRegExp::kDataUC16CodeOffset));
1022 __ Set(rcx, 0); // Type is two byte. 1008 __ Set(rcx, 0); // Type is two byte.
1023 __ jmp(&check_code); // Go to (E). 1009 __ jmp(&check_code); // Go to (E).
1024 1010
1025 // (10) Not a string or a short external string? If yes, bail out to runtime. 1011 // (10) Not a string or a short external string? If yes, bail out to runtime.
1026 __ bind(&not_long_external); 1012 __ bind(&not_long_external);
1027 // Catch non-string subject or short external string. 1013 // Catch non-string subject or short external string.
1028 STATIC_ASSERT(kNotStringTag != 0 && kShortExternalStringTag !=0); 1014 STATIC_ASSERT(kNotStringTag != 0 && kShortExternalStringTag !=0);
1029 __ testb(rbx, Immediate(kIsNotStringMask | kShortExternalStringMask)); 1015 __ testb(rbx, Immediate(kIsNotStringMask | kShortExternalStringMask));
1030 __ j(not_zero, &runtime); 1016 __ j(not_zero, &runtime);
1031 1017
1032 // (11) Sliced string. Replace subject with parent. Go to (5a). 1018 // (11) Sliced string. Replace subject with parent. Go to (1).
1033 // Load offset into r14 and replace subject string with parent. 1019 // Load offset into r14 and replace subject string with parent.
1034 __ SmiToInteger32(r14, FieldOperand(rdi, SlicedString::kOffsetOffset)); 1020 __ SmiToInteger32(r14, FieldOperand(rdi, SlicedString::kOffsetOffset));
1035 __ movp(rdi, FieldOperand(rdi, SlicedString::kParentOffset)); 1021 __ movp(rdi, FieldOperand(rdi, SlicedString::kParentOffset));
1036 __ jmp(&check_underlying); 1022 __ jmp(&check_underlying);
1037 #endif // V8_INTERPRETED_REGEXP 1023 #endif // V8_INTERPRETED_REGEXP
1038 } 1024 }
1039 1025
1040 1026
1041 static int NegativeComparisonResult(Condition cc) { 1027 static int NegativeComparisonResult(Condition cc) {
1042 DCHECK(cc != equal); 1028 DCHECK(cc != equal);
(...skipping 4600 matching lines...) Expand 10 before | Expand all | Expand 10 after
5643 NULL); 5629 NULL);
5644 } 5630 }
5645 5631
5646 5632
5647 #undef __ 5633 #undef __
5648 5634
5649 } // namespace internal 5635 } // namespace internal
5650 } // namespace v8 5636 } // namespace v8
5651 5637
5652 #endif // V8_TARGET_ARCH_X64 5638 #endif // V8_TARGET_ARCH_X64
OLDNEW
« no previous file with comments | « src/ppc/code-stubs-ppc.cc ('k') | src/x87/code-stubs-x87.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698