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

Side by Side Diff: src/IceInstARM32.h

Issue 1481133002: Subzero. ARM32. Show FP lowering some love. (Closed) Base URL: https://chromium.googlesource.com/native_client/pnacl-subzero.git@master
Patch Set: Handles comments; git pull; fixes lit tests. Created 5 years 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/IceCfgNode.cpp ('k') | src/IceInstARM32.cpp » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 //===- subzero/src/IceInstARM32.h - ARM32 machine instructions --*- C++ -*-===// 1 //===- subzero/src/IceInstARM32.h - ARM32 machine instructions --*- C++ -*-===//
2 // 2 //
3 // The Subzero Code Generator 3 // The Subzero Code Generator
4 // 4 //
5 // This file is distributed under the University of Illinois Open Source 5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details. 6 // License. See LICENSE.TXT for details.
7 // 7 //
8 //===----------------------------------------------------------------------===// 8 //===----------------------------------------------------------------------===//
9 /// 9 ///
10 /// \file 10 /// \file
(...skipping 397 matching lines...) Expand 10 before | Expand all | Expand 10 after
408 Tst, 408 Tst,
409 Udiv, 409 Udiv,
410 Umull, 410 Umull,
411 Uxt, 411 Uxt,
412 Vabs, 412 Vabs,
413 Vadd, 413 Vadd,
414 Vcmp, 414 Vcmp,
415 Vcvt, 415 Vcvt,
416 Vdiv, 416 Vdiv,
417 Veor, 417 Veor,
418 Vmla,
419 Vmls,
418 Vmrs, 420 Vmrs,
419 Vmul, 421 Vmul,
420 Vsqrt, 422 Vsqrt,
421 Vsub 423 Vsub
422 }; 424 };
423 425
424 static constexpr size_t InstSize = sizeof(uint32_t); 426 static constexpr size_t InstSize = sizeof(uint32_t);
425 427
426 static const char *getWidthString(Type Ty); 428 static const char *getWidthString(Type Ty);
427 static const char *getVecWidthString(Type Ty); 429 static const char *getVecWidthString(Type Ty);
428 static CondARM32::Cond getOppositeCondition(CondARM32::Cond Cond); 430 static CondARM32::Cond getOppositeCondition(CondARM32::Cond Cond);
429 431
430 /// Called inside derived methods emit() to communicate that multiple 432 /// Called inside derived methods emit() to communicate that multiple
431 /// instructions are being generated. Used by emitIAS() methods to 433 /// instructions are being generated. Used by emitIAS() methods to
432 /// generate textual fixups for instructions that are not yet 434 /// generate textual fixups for instructions that are not yet
433 /// implemented. 435 /// implemented.
434 void startNextInst(const Cfg *Func) const; 436 void startNextInst(const Cfg *Func) const;
435 437
436 /// Shared emit routines for common forms of instructions. 438 /// Shared emit routines for common forms of instructions.
437 static void emitThreeAddrFP(const char *Opcode, const InstARM32 *Inst, 439 static void emitThreeAddrFP(const char *Opcode, const InstARM32 *Inst,
438 const Cfg *Func); 440 const Cfg *Func);
441 static void emitFourAddrFP(const char *Opcode, const InstARM32 *Inst,
442 const Cfg *Func);
439 443
440 void dump(const Cfg *Func) const override; 444 void dump(const Cfg *Func) const override;
441 445
442 void emitIAS(const Cfg *Func) const override; 446 void emitIAS(const Cfg *Func) const override;
443 447
444 protected: 448 protected:
445 InstARM32(Cfg *Func, InstKindARM32 Kind, SizeT Maxsrcs, Variable *Dest) 449 InstARM32(Cfg *Func, InstKindARM32 Kind, SizeT Maxsrcs, Variable *Dest)
446 : InstTarget(Func, static_cast<InstKind>(Kind), Maxsrcs, Dest) {} 450 : InstTarget(Func, static_cast<InstKind>(Kind), Maxsrcs, Dest) {}
447 451
448 static bool isClassof(const Inst *Inst, InstKindARM32 MyKind) { 452 static bool isClassof(const Inst *Inst, InstKindARM32 MyKind) {
(...skipping 252 matching lines...) Expand 10 before | Expand all | Expand 10 after
701 addSource(Src1); 705 addSource(Src1);
702 } 706 }
703 707
704 static const char *Opcode; 708 static const char *Opcode;
705 bool SetFlags; 709 bool SetFlags;
706 }; 710 };
707 711
708 /// Instructions of the form x := y op z, for vector/FP. We leave these as 712 /// Instructions of the form x := y op z, for vector/FP. We leave these as
709 /// unconditional: "ARM deprecates the conditional execution of any instruction 713 /// unconditional: "ARM deprecates the conditional execution of any instruction
710 /// encoding provided by the Advanced SIMD Extension that is not also provided 714 /// encoding provided by the Advanced SIMD Extension that is not also provided
711 /// by the Floating-point (VFP) extension". They do not set flags. 715 /// by the floating-point (VFP) extension". They do not set flags.
712 template <InstARM32::InstKindARM32 K> 716 template <InstARM32::InstKindARM32 K>
713 class InstARM32ThreeAddrFP : public InstARM32 { 717 class InstARM32ThreeAddrFP : public InstARM32 {
714 InstARM32ThreeAddrFP() = delete; 718 InstARM32ThreeAddrFP() = delete;
715 InstARM32ThreeAddrFP(const InstARM32ThreeAddrFP &) = delete; 719 InstARM32ThreeAddrFP(const InstARM32ThreeAddrFP &) = delete;
716 InstARM32ThreeAddrFP &operator=(const InstARM32ThreeAddrFP &) = delete; 720 InstARM32ThreeAddrFP &operator=(const InstARM32ThreeAddrFP &) = delete;
717 721
718 public: 722 public:
719 /// Create a vector/FP binary-op instruction like vadd, and vsub. Everything 723 /// Create a vector/FP binary-op instruction like vadd, and vsub. Everything
720 /// must be a register. 724 /// must be a register.
721 static InstARM32ThreeAddrFP *create(Cfg *Func, Variable *Dest, Variable *Src0, 725 static InstARM32ThreeAddrFP *create(Cfg *Func, Variable *Dest, Variable *Src0,
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after
789 CondARM32::Cond Predicate) 793 CondARM32::Cond Predicate)
790 : InstARM32Pred(Func, K, 3, Dest, Predicate) { 794 : InstARM32Pred(Func, K, 3, Dest, Predicate) {
791 addSource(Src0); 795 addSource(Src0);
792 addSource(Src1); 796 addSource(Src1);
793 addSource(Src2); 797 addSource(Src2);
794 } 798 }
795 799
796 static const char *Opcode; 800 static const char *Opcode;
797 }; 801 };
798 802
803 /// Instructions of the form x := x op1 (y op2 z). E.g., multiply accumulate.
804 /// We leave these as unconditional: "ARM deprecates the conditional execution
805 /// of any instruction encoding provided by the Advanced SIMD Extension that is
806 /// not also provided by the floating-point (VFP) extension". They do not set
807 /// flags.
808 template <InstARM32::InstKindARM32 K>
809 class InstARM32FourAddrFP : public InstARM32 {
810 InstARM32FourAddrFP() = delete;
811 InstARM32FourAddrFP(const InstARM32FourAddrFP &) = delete;
812 InstARM32FourAddrFP &operator=(const InstARM32FourAddrFP &) = delete;
813
814 public:
815 // Every operand must be a register.
816 static InstARM32FourAddrFP *create(Cfg *Func, Variable *Dest, Variable *Src0,
817 Variable *Src1) {
818 return new (Func->allocate<InstARM32FourAddrFP>())
819 InstARM32FourAddrFP(Func, Dest, Src0, Src1);
820 }
821 void emit(const Cfg *Func) const override {
822 if (!BuildDefs::dump())
823 return;
824 emitFourAddrFP(Opcode, this, Func);
825 }
826 void emitIAS(const Cfg *Func) const override { emitUsingTextFixup(Func); }
827 void dump(const Cfg *Func) const override {
828 if (!BuildDefs::dump())
829 return;
830 Ostream &Str = Func->getContext()->getStrDump();
831 dumpDest(Func);
832 Str << " = ";
833 Str << Opcode << "." << getDest()->getType() << " ";
834 dumpDest(Func);
835 Str << ", ";
836 dumpSources(Func);
837 }
838 static bool classof(const Inst *Inst) { return isClassof(Inst, K); }
839
840 private:
841 InstARM32FourAddrFP(Cfg *Func, Variable *Dest, Variable *Src0, Variable *Src1)
842 : InstARM32(Func, K, 3, Dest) {
843 addSource(Dest);
844 addSource(Src0);
845 addSource(Src1);
846 }
847
848 static const char *Opcode;
849 };
850
799 /// Instructions of the form x cmpop y (setting flags). 851 /// Instructions of the form x cmpop y (setting flags).
800 template <InstARM32::InstKindARM32 K> 852 template <InstARM32::InstKindARM32 K>
801 class InstARM32CmpLike : public InstARM32Pred { 853 class InstARM32CmpLike : public InstARM32Pred {
802 InstARM32CmpLike() = delete; 854 InstARM32CmpLike() = delete;
803 InstARM32CmpLike(const InstARM32CmpLike &) = delete; 855 InstARM32CmpLike(const InstARM32CmpLike &) = delete;
804 InstARM32CmpLike &operator=(const InstARM32CmpLike &) = delete; 856 InstARM32CmpLike &operator=(const InstARM32CmpLike &) = delete;
805 857
806 public: 858 public:
807 static InstARM32CmpLike *create(Cfg *Func, Variable *Src0, Operand *Src1, 859 static InstARM32CmpLike *create(Cfg *Func, Variable *Src0, Operand *Src1,
808 CondARM32::Cond Predicate) { 860 CondARM32::Cond Predicate) {
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
848 using InstARM32Mul = InstARM32ThreeAddrGPR<InstARM32::Mul>; 900 using InstARM32Mul = InstARM32ThreeAddrGPR<InstARM32::Mul>;
849 using InstARM32Orr = InstARM32ThreeAddrGPR<InstARM32::Orr>; 901 using InstARM32Orr = InstARM32ThreeAddrGPR<InstARM32::Orr>;
850 using InstARM32Rsb = InstARM32ThreeAddrGPR<InstARM32::Rsb>; 902 using InstARM32Rsb = InstARM32ThreeAddrGPR<InstARM32::Rsb>;
851 using InstARM32Rsc = InstARM32ThreeAddrGPR<InstARM32::Rsc>; 903 using InstARM32Rsc = InstARM32ThreeAddrGPR<InstARM32::Rsc>;
852 using InstARM32Sbc = InstARM32ThreeAddrGPR<InstARM32::Sbc>; 904 using InstARM32Sbc = InstARM32ThreeAddrGPR<InstARM32::Sbc>;
853 using InstARM32Sdiv = InstARM32ThreeAddrGPR<InstARM32::Sdiv>; 905 using InstARM32Sdiv = InstARM32ThreeAddrGPR<InstARM32::Sdiv>;
854 using InstARM32Sub = InstARM32ThreeAddrGPR<InstARM32::Sub>; 906 using InstARM32Sub = InstARM32ThreeAddrGPR<InstARM32::Sub>;
855 using InstARM32Udiv = InstARM32ThreeAddrGPR<InstARM32::Udiv>; 907 using InstARM32Udiv = InstARM32ThreeAddrGPR<InstARM32::Udiv>;
856 using InstARM32Vadd = InstARM32ThreeAddrFP<InstARM32::Vadd>; 908 using InstARM32Vadd = InstARM32ThreeAddrFP<InstARM32::Vadd>;
857 using InstARM32Vdiv = InstARM32ThreeAddrFP<InstARM32::Vdiv>; 909 using InstARM32Vdiv = InstARM32ThreeAddrFP<InstARM32::Vdiv>;
910 using InstARM32Veor = InstARM32ThreeAddrFP<InstARM32::Veor>;
911 using InstARM32Vmla = InstARM32FourAddrFP<InstARM32::Vmla>;
912 using InstARM32Vmls = InstARM32FourAddrFP<InstARM32::Vmls>;
858 using InstARM32Vmul = InstARM32ThreeAddrFP<InstARM32::Vmul>; 913 using InstARM32Vmul = InstARM32ThreeAddrFP<InstARM32::Vmul>;
859 using InstARM32Veor = InstARM32ThreeAddrFP<InstARM32::Veor>;
860 using InstARM32Vsub = InstARM32ThreeAddrFP<InstARM32::Vsub>; 914 using InstARM32Vsub = InstARM32ThreeAddrFP<InstARM32::Vsub>;
861 using InstARM32Ldr = InstARM32LoadBase<InstARM32::Ldr>; 915 using InstARM32Ldr = InstARM32LoadBase<InstARM32::Ldr>;
862 using InstARM32Ldrex = InstARM32LoadBase<InstARM32::Ldrex>; 916 using InstARM32Ldrex = InstARM32LoadBase<InstARM32::Ldrex>;
863 /// MovT leaves the bottom bits alone so dest is also a source. This helps 917 /// MovT leaves the bottom bits alone so dest is also a source. This helps
864 /// indicate that a previous MovW setting dest is not dead code. 918 /// indicate that a previous MovW setting dest is not dead code.
865 using InstARM32Movt = InstARM32TwoAddrGPR<InstARM32::Movt>; 919 using InstARM32Movt = InstARM32TwoAddrGPR<InstARM32::Movt>;
866 using InstARM32Movw = InstARM32UnaryopGPR<InstARM32::Movw, false>; 920 using InstARM32Movw = InstARM32UnaryopGPR<InstARM32::Movw, false>;
867 using InstARM32Clz = InstARM32UnaryopGPR<InstARM32::Clz, false>; 921 using InstARM32Clz = InstARM32UnaryopGPR<InstARM32::Clz, false>;
868 using InstARM32Mvn = InstARM32UnaryopGPR<InstARM32::Mvn, false>; 922 using InstARM32Mvn = InstARM32UnaryopGPR<InstARM32::Mvn, false>;
869 using InstARM32Rbit = InstARM32UnaryopGPR<InstARM32::Rbit, false>; 923 using InstARM32Rbit = InstARM32UnaryopGPR<InstARM32::Rbit, false>;
(...skipping 124 matching lines...) Expand 10 before | Expand all | Expand 10 after
994 Operand *getCallTarget() const { return getSrc(0); } 1048 Operand *getCallTarget() const { return getSrc(0); }
995 void emit(const Cfg *Func) const override; 1049 void emit(const Cfg *Func) const override;
996 void emitIAS(const Cfg *Func) const override; 1050 void emitIAS(const Cfg *Func) const override;
997 void dump(const Cfg *Func) const override; 1051 void dump(const Cfg *Func) const override;
998 static bool classof(const Inst *Inst) { return isClassof(Inst, Call); } 1052 static bool classof(const Inst *Inst) { return isClassof(Inst, Call); }
999 1053
1000 private: 1054 private:
1001 InstARM32Call(Cfg *Func, Variable *Dest, Operand *CallTarget); 1055 InstARM32Call(Cfg *Func, Variable *Dest, Operand *CallTarget);
1002 }; 1056 };
1003 1057
1004 /// Pop into a list of GPRs. Technically this can be predicated, but we don't 1058 /// Pops a list of registers. It may be a list of GPRs, or a list of VFP "s"
1005 /// need that functionality. 1059 /// regs, but not both. In any case, the list must be sorted.
1006 class InstARM32Pop : public InstARM32 { 1060 class InstARM32Pop : public InstARM32 {
1007 InstARM32Pop() = delete; 1061 InstARM32Pop() = delete;
1008 InstARM32Pop(const InstARM32Pop &) = delete; 1062 InstARM32Pop(const InstARM32Pop &) = delete;
1009 InstARM32Pop &operator=(const InstARM32Pop &) = delete; 1063 InstARM32Pop &operator=(const InstARM32Pop &) = delete;
1010 1064
1011 public: 1065 public:
1012 static InstARM32Pop *create(Cfg *Func, const VarList &Dests) { 1066 static InstARM32Pop *create(Cfg *Func, const VarList &Dests) {
1013 return new (Func->allocate<InstARM32Pop>()) InstARM32Pop(Func, Dests); 1067 return new (Func->allocate<InstARM32Pop>()) InstARM32Pop(Func, Dests);
1014 } 1068 }
1015 void emit(const Cfg *Func) const override; 1069 void emit(const Cfg *Func) const override;
1016 void emitIAS(const Cfg *Func) const override; 1070 void emitIAS(const Cfg *Func) const override;
1017 void dump(const Cfg *Func) const override; 1071 void dump(const Cfg *Func) const override;
1018 static bool classof(const Inst *Inst) { return isClassof(Inst, Pop); } 1072 static bool classof(const Inst *Inst) { return isClassof(Inst, Pop); }
1019 1073
1020 private: 1074 private:
1021 InstARM32Pop(Cfg *Func, const VarList &Dests); 1075 InstARM32Pop(Cfg *Func, const VarList &Dests);
1022 1076
1023 VarList Dests; 1077 VarList Dests;
1024 }; 1078 };
1025 1079
1026 /// Push a list of GPRs. Technically this can be predicated, but we don't need 1080 /// Pushes a list of registers. Just like Pop (see above), the list may be of
1027 /// that functionality. 1081 /// GPRs, or VFP "s" registers, but not both.
1028 class InstARM32Push : public InstARM32 { 1082 class InstARM32Push : public InstARM32 {
1029 InstARM32Push() = delete; 1083 InstARM32Push() = delete;
1030 InstARM32Push(const InstARM32Push &) = delete; 1084 InstARM32Push(const InstARM32Push &) = delete;
1031 InstARM32Push &operator=(const InstARM32Push &) = delete; 1085 InstARM32Push &operator=(const InstARM32Push &) = delete;
1032 1086
1033 public: 1087 public:
1034 static InstARM32Push *create(Cfg *Func, const VarList &Srcs) { 1088 static InstARM32Push *create(Cfg *Func, const VarList &Srcs) {
1035 return new (Func->allocate<InstARM32Push>()) InstARM32Push(Func, Srcs); 1089 return new (Func->allocate<InstARM32Push>()) InstARM32Push(Func, Srcs);
1036 } 1090 }
1037 void emit(const Cfg *Func) const override; 1091 void emit(const Cfg *Func) const override;
(...skipping 279 matching lines...) Expand 10 before | Expand all | Expand 10 after
1317 // default implementations. Without this, there is the possibility of ODR 1371 // default implementations. Without this, there is the possibility of ODR
1318 // violations and link errors. 1372 // violations and link errors.
1319 1373
1320 template <> void InstARM32Ldr::emit(const Cfg *Func) const; 1374 template <> void InstARM32Ldr::emit(const Cfg *Func) const;
1321 template <> void InstARM32Movw::emit(const Cfg *Func) const; 1375 template <> void InstARM32Movw::emit(const Cfg *Func) const;
1322 template <> void InstARM32Movt::emit(const Cfg *Func) const; 1376 template <> void InstARM32Movt::emit(const Cfg *Func) const;
1323 1377
1324 } // end of namespace Ice 1378 } // end of namespace Ice
1325 1379
1326 #endif // SUBZERO_SRC_ICEINSTARM32_H 1380 #endif // SUBZERO_SRC_ICEINSTARM32_H
OLDNEW
« no previous file with comments | « src/IceCfgNode.cpp ('k') | src/IceInstARM32.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698