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

Side by Side Diff: runtime/vm/intrinsifier_x64.cc

Issue 1049933002: Implement bigint shift intrinsics on x64. (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 5 years, 8 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 | « runtime/vm/intrinsifier_mips.cc ('k') | runtime/vm/method_recognizer.h » ('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 (c) 2013, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_X64. 5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_X64.
6 #if defined(TARGET_ARCH_X64) 6 #if defined(TARGET_ARCH_X64)
7 7
8 #include "vm/intrinsifier.h" 8 #include "vm/intrinsifier.h"
9 9
10 #include "vm/assembler.h" 10 #include "vm/assembler.h"
(...skipping 707 matching lines...) Expand 10 before | Expand all | Expand 10 after
718 __ xorq(RAX, RCX); 718 __ xorq(RAX, RCX);
719 // BSR does not write the destination register if source is zero. Put a 1 in 719 // BSR does not write the destination register if source is zero. Put a 1 in
720 // the Smi tag bit to ensure BSR writes to destination register. 720 // the Smi tag bit to ensure BSR writes to destination register.
721 __ orq(RAX, Immediate(kSmiTagMask)); 721 __ orq(RAX, Immediate(kSmiTagMask));
722 __ bsrq(RAX, RAX); 722 __ bsrq(RAX, RAX);
723 __ SmiTag(RAX); 723 __ SmiTag(RAX);
724 __ ret(); 724 __ ret();
725 } 725 }
726 726
727 727
728 void Intrinsifier::Bigint_lsh(Assembler* assembler) {
729 // static void _lsh(Uint32List x_digits, int x_used, int n,
730 // Uint32List r_digits)
731
732 __ movq(RDI, Address(RSP, 4 * kWordSize)); // x_digits
733 __ movq(R8, Address(RSP, 3 * kWordSize)); // x_used is Smi
734 __ subq(R8, Immediate(2)); // x_used > 0, Smi. R8 = x_used - 1, round up.
735 __ sarq(R8, Immediate(2)); // R8 + 1 = number of digit pairs to read.
736 __ movq(RCX, Address(RSP, 2 * kWordSize)); // n is Smi
737 __ SmiUntag(RCX);
738 __ movq(RBX, Address(RSP, 1 * kWordSize)); // r_digits
739 __ movq(RSI, RCX);
740 __ sarq(RSI, Immediate(6)); // RSI = n ~/ (2*_DIGIT_BITS).
741 __ leaq(RBX, FieldAddress(RBX, RSI, TIMES_8, TypedData::data_offset()));
742 __ xorq(RAX, RAX); // RAX = 0.
743 __ movq(RDX, FieldAddress(RDI, R8, TIMES_8, TypedData::data_offset()));
744 __ shldq(RAX, RDX, RCX);
745 __ movq(Address(RBX, R8, TIMES_8, 2 * Bigint::kBytesPerDigit), RAX);
746 Label last;
747 __ cmpq(R8, Immediate(0));
748 __ j(EQUAL, &last, Assembler::kNearJump);
749 Label loop;
750 __ Bind(&loop);
751 __ movq(RAX, RDX);
752 __ movq(RDX,
753 FieldAddress(RDI, R8, TIMES_8,
754 TypedData::data_offset() - 2 * Bigint::kBytesPerDigit));
755 __ shldq(RAX, RDX, RCX);
756 __ movq(Address(RBX, R8, TIMES_8, 0), RAX);
757 __ decq(R8);
758 __ j(NOT_ZERO, &loop, Assembler::kNearJump);
759 __ Bind(&last);
760 __ xorq(RAX, RAX); // RAX = 0.
761 __ shldq(RDX, RAX, RCX);
762 __ movq(Address(RBX, 0), RDX);
763 // Returning Object::null() is not required, since this method is private.
764 __ ret();
765 }
766
767
768 void Intrinsifier::Bigint_rsh(Assembler* assembler) {
769 // static void _rsh(Uint32List x_digits, int x_used, int n,
770 // Uint32List r_digits)
771
772 __ movq(RDI, Address(RSP, 4 * kWordSize)); // x_digits
773 __ movq(R8, Address(RSP, 3 * kWordSize)); // x_used is Smi
774 __ subq(R8, Immediate(2)); // x_used > 0, Smi. R8 = x_used - 1, round up.
775 __ sarq(R8, Immediate(2));
776 __ movq(RCX, Address(RSP, 2 * kWordSize)); // n is Smi
777 __ SmiUntag(RCX);
778 __ movq(RBX, Address(RSP, 1 * kWordSize)); // r_digits
779 __ movq(RSI, RCX);
780 __ sarq(RSI, Immediate(6)); // RSI = n ~/ (2*_DIGIT_BITS).
781 __ leaq(RDI, FieldAddress(RDI, RSI, TIMES_8, TypedData::data_offset()));
782 __ movq(RDX, Address(RDI, 0));
783 __ subq(R8, RSI); // R8 + 1 = number of digit pairs to read.
784 Label last;
785 __ cmpq(R8, Immediate(0));
786 __ j(EQUAL, &last, Assembler::kNearJump);
787 __ xorq(R9, R9); // R9 = 0.
788 Label loop;
789 __ Bind(&loop);
790 __ movq(RAX, RDX);
791 __ movq(RDX, Address(RDI, R9, TIMES_8, 2 * Bigint::kBytesPerDigit));
792 __ shrdq(RAX, RDX, RCX);
793 __ movq(FieldAddress(RBX, R9, TIMES_8, TypedData::data_offset()), RAX);
794 __ incq(R9);
795 __ cmpq(R9, R8);
796 __ j(NOT_EQUAL, &loop, Assembler::kNearJump);
797 __ Bind(&last);
798 __ xorq(RAX, RAX); // RAX = 0.
799 __ shrdq(RDX, RAX, RCX);
800 __ movq(FieldAddress(RBX, R8, TIMES_8, TypedData::data_offset()), RDX);
801 // Returning Object::null() is not required, since this method is private.
802 __ ret();
803 }
804
805
728 void Intrinsifier::Bigint_absAdd(Assembler* assembler) { 806 void Intrinsifier::Bigint_absAdd(Assembler* assembler) {
729 // static void _absAdd(Uint32List digits, int used, 807 // static void _absAdd(Uint32List digits, int used,
730 // Uint32List a_digits, int a_used, 808 // Uint32List a_digits, int a_used,
731 // Uint32List r_digits) 809 // Uint32List r_digits)
732 810
733 __ movq(RDI, Address(RSP, 5 * kWordSize)); // digits 811 __ movq(RDI, Address(RSP, 5 * kWordSize)); // digits
734 __ movq(R8, Address(RSP, 4 * kWordSize)); // used is Smi 812 __ movq(R8, Address(RSP, 4 * kWordSize)); // used is Smi
735 __ addq(R8, Immediate(2)); // used > 0, Smi. R8 = used + 1, round up. 813 __ addq(R8, Immediate(2)); // used > 0, Smi. R8 = used + 1, round up.
736 __ sarq(R8, Immediate(2)); // R8 = number of digit pairs to process. 814 __ sarq(R8, Immediate(2)); // R8 = number of digit pairs to process.
737 __ movq(RSI, Address(RSP, 3 * kWordSize)); // a_digits 815 __ movq(RSI, Address(RSP, 3 * kWordSize)); // a_digits
(...skipping 1175 matching lines...) Expand 10 before | Expand all | Expand 10 after
1913 // Set return value to Isolate::current_tag_. 1991 // Set return value to Isolate::current_tag_.
1914 __ movq(RAX, Address(RBX, Isolate::current_tag_offset())); 1992 __ movq(RAX, Address(RBX, Isolate::current_tag_offset()));
1915 __ ret(); 1993 __ ret();
1916 } 1994 }
1917 1995
1918 #undef __ 1996 #undef __
1919 1997
1920 } // namespace dart 1998 } // namespace dart
1921 1999
1922 #endif // defined TARGET_ARCH_X64 2000 #endif // defined TARGET_ARCH_X64
OLDNEW
« no previous file with comments | « runtime/vm/intrinsifier_mips.cc ('k') | runtime/vm/method_recognizer.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698