OLD | NEW |
1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 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 #ifndef V8_ARM64_DECODER_ARM64_INL_H_ | 5 #ifndef V8_ARM64_DECODER_ARM64_INL_H_ |
6 #define V8_ARM64_DECODER_ARM64_INL_H_ | 6 #define V8_ARM64_DECODER_ARM64_INL_H_ |
7 | 7 |
8 #include "src/arm64/decoder-arm64.h" | 8 #include "src/arm64/decoder-arm64.h" |
9 #include "src/globals.h" | 9 #include "src/globals.h" |
10 #include "src/utils.h" | 10 #include "src/utils.h" |
(...skipping 195 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
206 } | 206 } |
207 | 207 |
208 | 208 |
209 template<typename V> | 209 template<typename V> |
210 void Decoder<V>::DecodeLoadStore(Instruction* instr) { | 210 void Decoder<V>::DecodeLoadStore(Instruction* instr) { |
211 DCHECK((instr->Bits(27, 24) == 0x8) || | 211 DCHECK((instr->Bits(27, 24) == 0x8) || |
212 (instr->Bits(27, 24) == 0x9) || | 212 (instr->Bits(27, 24) == 0x9) || |
213 (instr->Bits(27, 24) == 0xC) || | 213 (instr->Bits(27, 24) == 0xC) || |
214 (instr->Bits(27, 24) == 0xD) ); | 214 (instr->Bits(27, 24) == 0xD) ); |
215 | 215 |
| 216 if ((instr->Bit(28) == 0) && (instr->Bit(29) == 0) && (instr->Bit(26) == 1)) { |
| 217 DecodeNEONLoadStore(instr); |
| 218 return; |
| 219 } |
| 220 |
216 if (instr->Bit(24) == 0) { | 221 if (instr->Bit(24) == 0) { |
217 if (instr->Bit(28) == 0) { | 222 if (instr->Bit(28) == 0) { |
218 if (instr->Bit(29) == 0) { | 223 if (instr->Bit(29) == 0) { |
219 if (instr->Bit(26) == 0) { | 224 if (instr->Bit(26) == 0) { |
220 if (instr->Mask(0xA08000) == 0x800000 || | 225 if (instr->Mask(0xA08000) == 0x800000 || |
221 instr->Mask(0xA00000) == 0xA00000) { | 226 instr->Mask(0xA00000) == 0xA00000) { |
222 V::VisitUnallocated(instr); | 227 V::VisitUnallocated(instr); |
223 } else if (instr->Mask(0x808000) == 0) { | 228 } else if (instr->Mask(0x808000) == 0) { |
224 // Load/Store exclusive without acquire/release are unimplemented. | 229 // Load/Store exclusive without acquire/release are unimplemented. |
225 V::VisitUnimplemented(instr); | 230 V::VisitUnimplemented(instr); |
226 } else { | 231 } else { |
227 V::VisitLoadStoreAcquireRelease(instr); | 232 V::VisitLoadStoreAcquireRelease(instr); |
228 } | 233 } |
229 } else { | |
230 DecodeAdvSIMDLoadStore(instr); | |
231 } | 234 } |
232 } else { | 235 } else { |
233 if ((instr->Bits(31, 30) == 0x3) || | 236 if ((instr->Bits(31, 30) == 0x3) || |
234 (instr->Mask(0xC4400000) == 0x40000000)) { | 237 (instr->Mask(0xC4400000) == 0x40000000)) { |
235 V::VisitUnallocated(instr); | 238 V::VisitUnallocated(instr); |
236 } else { | 239 } else { |
237 if (instr->Bit(23) == 0) { | 240 if (instr->Bit(23) == 0) { |
238 if (instr->Mask(0xC4400000) == 0xC0400000) { | 241 if (instr->Mask(0xC4400000) == 0xC0400000) { |
239 V::VisitUnallocated(instr); | 242 V::VisitUnallocated(instr); |
240 } else { | 243 } else { |
(...skipping 265 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
506 } | 509 } |
507 } | 510 } |
508 | 511 |
509 | 512 |
510 template<typename V> | 513 template<typename V> |
511 void Decoder<V>::DecodeFP(Instruction* instr) { | 514 void Decoder<V>::DecodeFP(Instruction* instr) { |
512 DCHECK((instr->Bits(27, 24) == 0xE) || | 515 DCHECK((instr->Bits(27, 24) == 0xE) || |
513 (instr->Bits(27, 24) == 0xF) ); | 516 (instr->Bits(27, 24) == 0xF) ); |
514 | 517 |
515 if (instr->Bit(28) == 0) { | 518 if (instr->Bit(28) == 0) { |
516 DecodeAdvSIMDDataProcessing(instr); | 519 DecodeNEONVectorDataProcessing(instr); |
517 } else { | 520 } else { |
518 if (instr->Bit(29) == 1) { | 521 if (instr->Bits(31, 30) == 0x3) { |
519 V::VisitUnallocated(instr); | 522 V::VisitUnallocated(instr); |
| 523 } else if (instr->Bits(31, 30) == 0x1) { |
| 524 DecodeNEONScalarDataProcessing(instr); |
520 } else { | 525 } else { |
521 if (instr->Bits(31, 30) == 0x3) { | 526 if (instr->Bit(29) == 0) { |
522 V::VisitUnallocated(instr); | |
523 } else if (instr->Bits(31, 30) == 0x1) { | |
524 DecodeAdvSIMDDataProcessing(instr); | |
525 } else { | |
526 if (instr->Bit(24) == 0) { | 527 if (instr->Bit(24) == 0) { |
527 if (instr->Bit(21) == 0) { | 528 if (instr->Bit(21) == 0) { |
528 if ((instr->Bit(23) == 1) || | 529 if ((instr->Bit(23) == 1) || |
529 (instr->Bit(18) == 1) || | 530 (instr->Bit(18) == 1) || |
530 (instr->Mask(0x80008000) == 0x00000000) || | 531 (instr->Mask(0x80008000) == 0x00000000) || |
531 (instr->Mask(0x000E0000) == 0x00000000) || | 532 (instr->Mask(0x000E0000) == 0x00000000) || |
532 (instr->Mask(0x000E0000) == 0x000A0000) || | 533 (instr->Mask(0x000E0000) == 0x000A0000) || |
533 (instr->Mask(0x00160000) == 0x00000000) || | 534 (instr->Mask(0x00160000) == 0x00000000) || |
534 (instr->Mask(0x00160000) == 0x00120000)) { | 535 (instr->Mask(0x00160000) == 0x00120000)) { |
535 V::VisitUnallocated(instr); | 536 V::VisitUnallocated(instr); |
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
622 } | 623 } |
623 } else { | 624 } else { |
624 // Bit 30 == 1 has been handled earlier. | 625 // Bit 30 == 1 has been handled earlier. |
625 DCHECK(instr->Bit(30) == 0); | 626 DCHECK(instr->Bit(30) == 0); |
626 if (instr->Mask(0xA0800000) != 0) { | 627 if (instr->Mask(0xA0800000) != 0) { |
627 V::VisitUnallocated(instr); | 628 V::VisitUnallocated(instr); |
628 } else { | 629 } else { |
629 V::VisitFPDataProcessing3Source(instr); | 630 V::VisitFPDataProcessing3Source(instr); |
630 } | 631 } |
631 } | 632 } |
| 633 } else { |
| 634 V::VisitUnallocated(instr); |
| 635 } |
| 636 } |
| 637 } |
| 638 } |
| 639 |
| 640 template <typename V> |
| 641 void Decoder<V>::DecodeNEONLoadStore(Instruction* instr) { |
| 642 DCHECK(instr->Bits(29, 25) == 0x6); |
| 643 if (instr->Bit(31) == 0) { |
| 644 if ((instr->Bit(24) == 0) && (instr->Bit(21) == 1)) { |
| 645 V::VisitUnallocated(instr); |
| 646 return; |
| 647 } |
| 648 |
| 649 if (instr->Bit(23) == 0) { |
| 650 if (instr->Bits(20, 16) == 0) { |
| 651 if (instr->Bit(24) == 0) { |
| 652 V::VisitNEONLoadStoreMultiStruct(instr); |
| 653 } else { |
| 654 V::VisitNEONLoadStoreSingleStruct(instr); |
| 655 } |
| 656 } else { |
| 657 V::VisitUnallocated(instr); |
| 658 } |
| 659 } else { |
| 660 if (instr->Bit(24) == 0) { |
| 661 V::VisitNEONLoadStoreMultiStructPostIndex(instr); |
| 662 } else { |
| 663 V::VisitNEONLoadStoreSingleStructPostIndex(instr); |
| 664 } |
| 665 } |
| 666 } else { |
| 667 V::VisitUnallocated(instr); |
| 668 } |
| 669 } |
| 670 |
| 671 template <typename V> |
| 672 void Decoder<V>::DecodeNEONVectorDataProcessing(Instruction* instr) { |
| 673 DCHECK(instr->Bits(28, 25) == 0x7); |
| 674 if (instr->Bit(31) == 0) { |
| 675 if (instr->Bit(24) == 0) { |
| 676 if (instr->Bit(21) == 0) { |
| 677 if (instr->Bit(15) == 0) { |
| 678 if (instr->Bit(10) == 0) { |
| 679 if (instr->Bit(29) == 0) { |
| 680 if (instr->Bit(11) == 0) { |
| 681 V::VisitNEONTable(instr); |
| 682 } else { |
| 683 V::VisitNEONPerm(instr); |
| 684 } |
| 685 } else { |
| 686 V::VisitNEONExtract(instr); |
| 687 } |
| 688 } else { |
| 689 if (instr->Bits(23, 22) == 0) { |
| 690 V::VisitNEONCopy(instr); |
| 691 } else { |
| 692 V::VisitUnallocated(instr); |
| 693 } |
| 694 } |
| 695 } else { |
| 696 V::VisitUnallocated(instr); |
| 697 } |
| 698 } else { |
| 699 if (instr->Bit(10) == 0) { |
| 700 if (instr->Bit(11) == 0) { |
| 701 V::VisitNEON3Different(instr); |
| 702 } else { |
| 703 if (instr->Bits(18, 17) == 0) { |
| 704 if (instr->Bit(20) == 0) { |
| 705 if (instr->Bit(19) == 0) { |
| 706 V::VisitNEON2RegMisc(instr); |
| 707 } else { |
| 708 if (instr->Bits(30, 29) == 0x2) { |
| 709 V::VisitUnallocated(instr); |
| 710 } else { |
| 711 V::VisitUnallocated(instr); |
| 712 } |
| 713 } |
| 714 } else { |
| 715 if (instr->Bit(19) == 0) { |
| 716 V::VisitNEONAcrossLanes(instr); |
| 717 } else { |
| 718 V::VisitUnallocated(instr); |
| 719 } |
| 720 } |
| 721 } else { |
| 722 V::VisitUnallocated(instr); |
| 723 } |
| 724 } |
| 725 } else { |
| 726 V::VisitNEON3Same(instr); |
| 727 } |
| 728 } |
| 729 } else { |
| 730 if (instr->Bit(10) == 0) { |
| 731 V::VisitNEONByIndexedElement(instr); |
| 732 } else { |
| 733 if (instr->Bit(23) == 0) { |
| 734 if (instr->Bits(22, 19) == 0) { |
| 735 V::VisitNEONModifiedImmediate(instr); |
| 736 } else { |
| 737 V::VisitNEONShiftImmediate(instr); |
| 738 } |
| 739 } else { |
| 740 V::VisitUnallocated(instr); |
| 741 } |
| 742 } |
| 743 } |
| 744 } else { |
| 745 V::VisitUnallocated(instr); |
| 746 } |
| 747 } |
| 748 |
| 749 template <typename V> |
| 750 void Decoder<V>::DecodeNEONScalarDataProcessing(Instruction* instr) { |
| 751 DCHECK(instr->Bits(28, 25) == 0xF); |
| 752 if (instr->Bit(24) == 0) { |
| 753 if (instr->Bit(21) == 0) { |
| 754 if (instr->Bit(15) == 0) { |
| 755 if (instr->Bit(10) == 0) { |
| 756 if (instr->Bit(29) == 0) { |
| 757 if (instr->Bit(11) == 0) { |
| 758 V::VisitUnallocated(instr); |
| 759 } else { |
| 760 V::VisitUnallocated(instr); |
| 761 } |
| 762 } else { |
| 763 V::VisitUnallocated(instr); |
| 764 } |
| 765 } else { |
| 766 if (instr->Bits(23, 22) == 0) { |
| 767 V::VisitNEONScalarCopy(instr); |
| 768 } else { |
| 769 V::VisitUnallocated(instr); |
| 770 } |
| 771 } |
| 772 } else { |
| 773 V::VisitUnallocated(instr); |
| 774 } |
| 775 } else { |
| 776 if (instr->Bit(10) == 0) { |
| 777 if (instr->Bit(11) == 0) { |
| 778 V::VisitNEONScalar3Diff(instr); |
| 779 } else { |
| 780 if (instr->Bits(18, 17) == 0) { |
| 781 if (instr->Bit(20) == 0) { |
| 782 if (instr->Bit(19) == 0) { |
| 783 V::VisitNEONScalar2RegMisc(instr); |
| 784 } else { |
| 785 if (instr->Bit(29) == 0) { |
| 786 V::VisitUnallocated(instr); |
| 787 } else { |
| 788 V::VisitUnallocated(instr); |
| 789 } |
| 790 } |
| 791 } else { |
| 792 if (instr->Bit(19) == 0) { |
| 793 V::VisitNEONScalarPairwise(instr); |
| 794 } else { |
| 795 V::VisitUnallocated(instr); |
| 796 } |
| 797 } |
| 798 } else { |
| 799 V::VisitUnallocated(instr); |
| 800 } |
| 801 } |
| 802 } else { |
| 803 V::VisitNEONScalar3Same(instr); |
| 804 } |
| 805 } |
| 806 } else { |
| 807 if (instr->Bit(10) == 0) { |
| 808 V::VisitNEONScalarByIndexedElement(instr); |
| 809 } else { |
| 810 if (instr->Bit(23) == 0) { |
| 811 V::VisitNEONScalarShiftImmediate(instr); |
| 812 } else { |
| 813 V::VisitUnallocated(instr); |
632 } | 814 } |
633 } | 815 } |
634 } | 816 } |
635 } | 817 } |
636 | 818 |
637 | 819 |
638 template<typename V> | |
639 void Decoder<V>::DecodeAdvSIMDLoadStore(Instruction* instr) { | |
640 // TODO(all): Implement Advanced SIMD load/store instruction decode. | |
641 DCHECK(instr->Bits(29, 25) == 0x6); | |
642 V::VisitUnimplemented(instr); | |
643 } | |
644 | |
645 | |
646 template<typename V> | |
647 void Decoder<V>::DecodeAdvSIMDDataProcessing(Instruction* instr) { | |
648 // TODO(all): Implement Advanced SIMD data processing instruction decode. | |
649 DCHECK(instr->Bits(27, 25) == 0x7); | |
650 V::VisitUnimplemented(instr); | |
651 } | |
652 | |
653 | |
654 } // namespace internal | 820 } // namespace internal |
655 } // namespace v8 | 821 } // namespace v8 |
656 | 822 |
657 #endif // V8_ARM64_DECODER_ARM64_INL_H_ | 823 #endif // V8_ARM64_DECODER_ARM64_INL_H_ |
OLD | NEW |