12036f446SAditya Nandakumar //===- PatternMatchTest.cpp -----------------------------------------------===//
22036f446SAditya Nandakumar //
32946cd70SChandler Carruth // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
42946cd70SChandler Carruth // See https://llvm.org/LICENSE.txt for license information.
52946cd70SChandler Carruth // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
62036f446SAditya Nandakumar //
72036f446SAditya Nandakumar //===----------------------------------------------------------------------===//
82036f446SAditya Nandakumar 
9ff384481SMarcello Maggioni #include "GISelMITest.h"
102036f446SAditya Nandakumar #include "llvm/CodeGen/GlobalISel/MIPatternMatch.h"
112036f446SAditya Nandakumar #include "llvm/CodeGen/GlobalISel/MachineIRBuilder.h"
122036f446SAditya Nandakumar #include "llvm/CodeGen/GlobalISel/Utils.h"
132036f446SAditya Nandakumar #include "llvm/CodeGen/MIRParser/MIRParser.h"
142036f446SAditya Nandakumar #include "llvm/CodeGen/MachineFunction.h"
152036f446SAditya Nandakumar #include "llvm/CodeGen/MachineModuleInfo.h"
162036f446SAditya Nandakumar #include "llvm/CodeGen/TargetFrameLowering.h"
172036f446SAditya Nandakumar #include "llvm/CodeGen/TargetInstrInfo.h"
182036f446SAditya Nandakumar #include "llvm/CodeGen/TargetLowering.h"
192036f446SAditya Nandakumar #include "llvm/CodeGen/TargetSubtargetInfo.h"
2089b57061SReid Kleckner #include "llvm/MC/TargetRegistry.h"
212036f446SAditya Nandakumar #include "llvm/Support/SourceMgr.h"
222036f446SAditya Nandakumar #include "llvm/Support/TargetSelect.h"
232036f446SAditya Nandakumar #include "llvm/Target/TargetMachine.h"
242036f446SAditya Nandakumar #include "llvm/Target/TargetOptions.h"
252036f446SAditya Nandakumar #include "gtest/gtest.h"
262036f446SAditya Nandakumar 
272036f446SAditya Nandakumar using namespace llvm;
282036f446SAditya Nandakumar using namespace MIPatternMatch;
292036f446SAditya Nandakumar 
302036f446SAditya Nandakumar namespace {
312036f446SAditya Nandakumar 
TEST_F(AArch64GISelMITest,MatchIntConstant)3258f843a5SMatt Arsenault TEST_F(AArch64GISelMITest, MatchIntConstant) {
3342a84d22SDaniel Sanders   setUp();
342036f446SAditya Nandakumar   if (!TM)
352036f446SAditya Nandakumar     return;
362036f446SAditya Nandakumar   auto MIBCst = B.buildConstant(LLT::scalar(64), 42);
37b808e3adSAditya Nandakumar   int64_t Cst;
38b482e1bfSJay Foad   bool match = mi_match(MIBCst.getReg(0), *MRI, m_ICst(Cst));
39b3e86709SMatt Arsenault   EXPECT_TRUE(match);
40b3e86709SMatt Arsenault   EXPECT_EQ(Cst, 42);
412036f446SAditya Nandakumar }
422036f446SAditya Nandakumar 
TEST_F(AArch64GISelMITest,MatchIntConstantRegister)43ebe408adSPetar Avramovic TEST_F(AArch64GISelMITest, MatchIntConstantRegister) {
44ebe408adSPetar Avramovic   setUp();
45ebe408adSPetar Avramovic   if (!TM)
46ebe408adSPetar Avramovic     return;
47ebe408adSPetar Avramovic   auto MIBCst = B.buildConstant(LLT::scalar(64), 42);
48d477a7c2SPetar Avramovic   Optional<ValueAndVReg> Src0;
49d477a7c2SPetar Avramovic   bool match = mi_match(MIBCst.getReg(0), *MRI, m_GCst(Src0));
50ebe408adSPetar Avramovic   EXPECT_TRUE(match);
51d477a7c2SPetar Avramovic   EXPECT_EQ(Src0->VReg, MIBCst.getReg(0));
52ebe408adSPetar Avramovic }
53ebe408adSPetar Avramovic 
TEST_F(AArch64GISelMITest,MatchIntConstantSplat)54*485dd0b7SAbinav Puthan Purayil TEST_F(AArch64GISelMITest, MatchIntConstantSplat) {
55*485dd0b7SAbinav Puthan Purayil   setUp();
56*485dd0b7SAbinav Puthan Purayil   if (!TM)
57*485dd0b7SAbinav Puthan Purayil     return;
58*485dd0b7SAbinav Puthan Purayil 
59*485dd0b7SAbinav Puthan Purayil   LLT s64 = LLT::scalar(64);
60*485dd0b7SAbinav Puthan Purayil   LLT v4s64 = LLT::fixed_vector(4, s64);
61*485dd0b7SAbinav Puthan Purayil 
62*485dd0b7SAbinav Puthan Purayil   MachineInstrBuilder FortyTwoSplat =
63*485dd0b7SAbinav Puthan Purayil       B.buildSplatVector(v4s64, B.buildConstant(s64, 42));
64*485dd0b7SAbinav Puthan Purayil   int64_t Cst;
65*485dd0b7SAbinav Puthan Purayil   EXPECT_TRUE(mi_match(FortyTwoSplat.getReg(0), *MRI, m_ICstOrSplat(Cst)));
66*485dd0b7SAbinav Puthan Purayil   EXPECT_EQ(Cst, 42);
67*485dd0b7SAbinav Puthan Purayil 
68*485dd0b7SAbinav Puthan Purayil   MachineInstrBuilder NonConstantSplat =
69*485dd0b7SAbinav Puthan Purayil       B.buildBuildVector(v4s64, {Copies[0], Copies[0], Copies[0], Copies[0]});
70*485dd0b7SAbinav Puthan Purayil   EXPECT_FALSE(mi_match(NonConstantSplat.getReg(0), *MRI, m_ICstOrSplat(Cst)));
71*485dd0b7SAbinav Puthan Purayil }
72*485dd0b7SAbinav Puthan Purayil 
TEST_F(AArch64GISelMITest,MachineInstrPtrBind)7339662abfSPetar Avramovic TEST_F(AArch64GISelMITest, MachineInstrPtrBind) {
7439662abfSPetar Avramovic   setUp();
7539662abfSPetar Avramovic   if (!TM)
7639662abfSPetar Avramovic     return;
7739662abfSPetar Avramovic   auto MIBAdd = B.buildAdd(LLT::scalar(64), Copies[0], Copies[1]);
7839662abfSPetar Avramovic   // Test 'MachineInstr *' bind.
7939662abfSPetar Avramovic   // Default mi_match.
8039662abfSPetar Avramovic   MachineInstr *MIPtr = MIBAdd.getInstr();
8139662abfSPetar Avramovic   bool match = mi_match(MIPtr, *MRI, m_GAdd(m_Reg(), m_Reg()));
8239662abfSPetar Avramovic   EXPECT_TRUE(match);
8339662abfSPetar Avramovic   // Specialized mi_match for MachineInstr &.
8439662abfSPetar Avramovic   MachineInstr &MI = *MIBAdd.getInstr();
8539662abfSPetar Avramovic   match = mi_match(MI, *MRI, m_GAdd(m_Reg(), m_Reg()));
8639662abfSPetar Avramovic   EXPECT_TRUE(match);
8739662abfSPetar Avramovic   // MachineInstrBuilder has automatic conversion to MachineInstr *.
8839662abfSPetar Avramovic   match = mi_match(MIBAdd, *MRI, m_GAdd(m_Reg(), m_Reg()));
8939662abfSPetar Avramovic   EXPECT_TRUE(match);
9039662abfSPetar Avramovic   // Match instruction without def.
9139662abfSPetar Avramovic   auto MIBBrcond = B.buildBrCond(Copies[0], B.getMBB());
9239662abfSPetar Avramovic   MachineInstr *MatchedMI;
9339662abfSPetar Avramovic   match = mi_match(MIBBrcond, *MRI, m_MInstr(MatchedMI));
9439662abfSPetar Avramovic   EXPECT_TRUE(match);
9539662abfSPetar Avramovic   EXPECT_TRUE(MIBBrcond.getInstr() == MatchedMI);
9639662abfSPetar Avramovic   // Match instruction with two defs.
9739662abfSPetar Avramovic   auto MIBUAddO =
9839662abfSPetar Avramovic       B.buildUAddo(LLT::scalar(64), LLT::scalar(1), Copies[0], Copies[1]);
9939662abfSPetar Avramovic   match = mi_match(MIBUAddO, *MRI, m_MInstr(MatchedMI));
10039662abfSPetar Avramovic   EXPECT_TRUE(match);
10139662abfSPetar Avramovic   EXPECT_TRUE(MIBUAddO.getInstr() == MatchedMI);
10239662abfSPetar Avramovic }
10339662abfSPetar Avramovic 
TEST_F(AArch64GISelMITest,MatchBinaryOp)10458f843a5SMatt Arsenault TEST_F(AArch64GISelMITest, MatchBinaryOp) {
10542a84d22SDaniel Sanders   setUp();
1062036f446SAditya Nandakumar   if (!TM)
1072036f446SAditya Nandakumar     return;
108323db5d6SMatt Arsenault   LLT s32 = LLT::scalar(32);
1092036f446SAditya Nandakumar   LLT s64 = LLT::scalar(64);
110ddcb0aaeSJessica Paquette   LLT p0 = LLT::pointer(0, 64);
1112036f446SAditya Nandakumar   auto MIBAdd = B.buildAdd(s64, Copies[0], Copies[1]);
1122036f446SAditya Nandakumar   // Test case for no bind.
1132036f446SAditya Nandakumar   bool match =
114b482e1bfSJay Foad       mi_match(MIBAdd.getReg(0), *MRI, m_GAdd(m_Reg(), m_Reg()));
115b3e86709SMatt Arsenault   EXPECT_TRUE(match);
116e3a676e9SMatt Arsenault   Register Src0, Src1, Src2;
117b482e1bfSJay Foad   match = mi_match(MIBAdd.getReg(0), *MRI,
1182036f446SAditya Nandakumar                    m_GAdd(m_Reg(Src0), m_Reg(Src1)));
119b3e86709SMatt Arsenault   EXPECT_TRUE(match);
120b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
121b3e86709SMatt Arsenault   EXPECT_EQ(Src1, Copies[1]);
1222036f446SAditya Nandakumar 
1232036f446SAditya Nandakumar   // Build MUL(ADD %0, %1), %2
1242036f446SAditya Nandakumar   auto MIBMul = B.buildMul(s64, MIBAdd, Copies[2]);
1252036f446SAditya Nandakumar 
1262036f446SAditya Nandakumar   // Try to match MUL.
127b482e1bfSJay Foad   match = mi_match(MIBMul.getReg(0), *MRI,
1282036f446SAditya Nandakumar                    m_GMul(m_Reg(Src0), m_Reg(Src1)));
129b3e86709SMatt Arsenault   EXPECT_TRUE(match);
130b482e1bfSJay Foad   EXPECT_EQ(Src0, MIBAdd.getReg(0));
131b3e86709SMatt Arsenault   EXPECT_EQ(Src1, Copies[2]);
1322036f446SAditya Nandakumar 
1332036f446SAditya Nandakumar   // Try to match MUL(ADD)
134b482e1bfSJay Foad   match = mi_match(MIBMul.getReg(0), *MRI,
1352036f446SAditya Nandakumar                    m_GMul(m_GAdd(m_Reg(Src0), m_Reg(Src1)), m_Reg(Src2)));
136b3e86709SMatt Arsenault   EXPECT_TRUE(match);
137b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
138b3e86709SMatt Arsenault   EXPECT_EQ(Src1, Copies[1]);
139b3e86709SMatt Arsenault   EXPECT_EQ(Src2, Copies[2]);
1402036f446SAditya Nandakumar 
1412036f446SAditya Nandakumar   // Test Commutativity.
1422036f446SAditya Nandakumar   auto MIBMul2 = B.buildMul(s64, Copies[0], B.buildConstant(s64, 42));
1432036f446SAditya Nandakumar   // Try to match MUL(Cst, Reg) on src of MUL(Reg, Cst) to validate
1442036f446SAditya Nandakumar   // commutativity.
145b808e3adSAditya Nandakumar   int64_t Cst;
146b482e1bfSJay Foad   match = mi_match(MIBMul2.getReg(0), *MRI,
1472036f446SAditya Nandakumar                    m_GMul(m_ICst(Cst), m_Reg(Src0)));
148b3e86709SMatt Arsenault   EXPECT_TRUE(match);
149b3e86709SMatt Arsenault   EXPECT_EQ(Cst, 42);
150b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
1512036f446SAditya Nandakumar 
1522036f446SAditya Nandakumar   // Make sure commutative doesn't work with something like SUB.
1532036f446SAditya Nandakumar   auto MIBSub = B.buildSub(s64, Copies[0], B.buildConstant(s64, 42));
154b482e1bfSJay Foad   match = mi_match(MIBSub.getReg(0), *MRI,
1552036f446SAditya Nandakumar                    m_GSub(m_ICst(Cst), m_Reg(Src0)));
156b3e86709SMatt Arsenault   EXPECT_FALSE(match);
1576250b188SAditya Nandakumar 
158cef44a23SAditya Nandakumar   auto MIBFMul = B.buildInstr(TargetOpcode::G_FMUL, {s64},
159cef44a23SAditya Nandakumar                               {Copies[0], B.buildConstant(s64, 42)});
1606250b188SAditya Nandakumar   // Match and test commutativity for FMUL.
161b482e1bfSJay Foad   match = mi_match(MIBFMul.getReg(0), *MRI,
1626250b188SAditya Nandakumar                    m_GFMul(m_ICst(Cst), m_Reg(Src0)));
163b3e86709SMatt Arsenault   EXPECT_TRUE(match);
164b3e86709SMatt Arsenault   EXPECT_EQ(Cst, 42);
165b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
16602bb1747SVolkan Keles 
1672980b019SAditya Nandakumar   // FSUB
168cef44a23SAditya Nandakumar   auto MIBFSub = B.buildInstr(TargetOpcode::G_FSUB, {s64},
169cef44a23SAditya Nandakumar                               {Copies[0], B.buildConstant(s64, 42)});
170b482e1bfSJay Foad   match = mi_match(MIBFSub.getReg(0), *MRI,
1712980b019SAditya Nandakumar                    m_GFSub(m_Reg(Src0), m_Reg()));
172b3e86709SMatt Arsenault   EXPECT_TRUE(match);
173b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
1742980b019SAditya Nandakumar 
17502bb1747SVolkan Keles   // Build AND %0, %1
17602bb1747SVolkan Keles   auto MIBAnd = B.buildAnd(s64, Copies[0], Copies[1]);
17702bb1747SVolkan Keles   // Try to match AND.
178b482e1bfSJay Foad   match = mi_match(MIBAnd.getReg(0), *MRI,
17902bb1747SVolkan Keles                    m_GAnd(m_Reg(Src0), m_Reg(Src1)));
180b3e86709SMatt Arsenault   EXPECT_TRUE(match);
181b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
182b3e86709SMatt Arsenault   EXPECT_EQ(Src1, Copies[1]);
18302bb1747SVolkan Keles 
18402bb1747SVolkan Keles   // Build OR %0, %1
18502bb1747SVolkan Keles   auto MIBOr = B.buildOr(s64, Copies[0], Copies[1]);
18602bb1747SVolkan Keles   // Try to match OR.
187b482e1bfSJay Foad   match = mi_match(MIBOr.getReg(0), *MRI,
18802bb1747SVolkan Keles                    m_GOr(m_Reg(Src0), m_Reg(Src1)));
189b3e86709SMatt Arsenault   EXPECT_TRUE(match);
190b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
191b3e86709SMatt Arsenault   EXPECT_EQ(Src1, Copies[1]);
192323db5d6SMatt Arsenault 
193323db5d6SMatt Arsenault   // Match lshr, and make sure a different shift amount type works.
194323db5d6SMatt Arsenault   auto TruncCopy1 = B.buildTrunc(s32, Copies[1]);
195323db5d6SMatt Arsenault   auto LShr = B.buildLShr(s64, Copies[0], TruncCopy1);
196323db5d6SMatt Arsenault   match = mi_match(LShr.getReg(0), *MRI,
197323db5d6SMatt Arsenault                    m_GLShr(m_Reg(Src0), m_Reg(Src1)));
198323db5d6SMatt Arsenault   EXPECT_TRUE(match);
199323db5d6SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
200323db5d6SMatt Arsenault   EXPECT_EQ(Src1, TruncCopy1.getReg(0));
201cce3d96bSMatt Arsenault 
202cce3d96bSMatt Arsenault   // Match shl, and make sure a different shift amount type works.
203cce3d96bSMatt Arsenault   auto Shl = B.buildShl(s64, Copies[0], TruncCopy1);
204cce3d96bSMatt Arsenault   match = mi_match(Shl.getReg(0), *MRI,
205cce3d96bSMatt Arsenault                    m_GShl(m_Reg(Src0), m_Reg(Src1)));
206cce3d96bSMatt Arsenault   EXPECT_TRUE(match);
207cce3d96bSMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
208cce3d96bSMatt Arsenault   EXPECT_EQ(Src1, TruncCopy1.getReg(0));
209ddcb0aaeSJessica Paquette 
210ddcb0aaeSJessica Paquette   // Build a G_PTR_ADD and check that we can match it.
211ddcb0aaeSJessica Paquette   auto PtrAdd = B.buildPtrAdd(p0, {B.buildUndef(p0)}, Copies[0]);
212ddcb0aaeSJessica Paquette   match = mi_match(PtrAdd.getReg(0), *MRI, m_GPtrAdd(m_Reg(Src0), m_Reg(Src1)));
213ddcb0aaeSJessica Paquette   EXPECT_TRUE(match);
214ddcb0aaeSJessica Paquette   EXPECT_EQ(Src0, PtrAdd->getOperand(1).getReg());
215ddcb0aaeSJessica Paquette   EXPECT_EQ(Src1, Copies[0]);
2164c6eb388SPetar Avramovic 
2174c6eb388SPetar Avramovic   auto MIBCst = B.buildConstant(s64, 42);
2184c6eb388SPetar Avramovic   auto MIBAddCst = B.buildAdd(s64, MIBCst, Copies[0]);
2194c6eb388SPetar Avramovic   auto MIBUnmerge = B.buildUnmerge({s32, s32}, B.buildConstant(s64, 42));
2204c6eb388SPetar Avramovic 
2214c6eb388SPetar Avramovic   // m_BinOp with opcode.
2224c6eb388SPetar Avramovic   // Match binary instruction, opcode and its non-commutative operands.
2234c6eb388SPetar Avramovic   match = mi_match(MIBAddCst, *MRI,
2244c6eb388SPetar Avramovic                    m_BinOp(TargetOpcode::G_ADD, m_ICst(Cst), m_Reg(Src0)));
2254c6eb388SPetar Avramovic   EXPECT_TRUE(match);
2264c6eb388SPetar Avramovic   EXPECT_EQ(Src0, Copies[0]);
2274c6eb388SPetar Avramovic   EXPECT_EQ(Cst, 42);
2284c6eb388SPetar Avramovic 
2294c6eb388SPetar Avramovic   // Opcode doesn't match.
2304c6eb388SPetar Avramovic   match = mi_match(MIBAddCst, *MRI,
2314c6eb388SPetar Avramovic                    m_BinOp(TargetOpcode::G_MUL, m_ICst(Cst), m_Reg(Src0)));
2324c6eb388SPetar Avramovic   EXPECT_FALSE(match);
2334c6eb388SPetar Avramovic 
2344c6eb388SPetar Avramovic   match = mi_match(MIBAddCst, *MRI,
2354c6eb388SPetar Avramovic                    m_BinOp(TargetOpcode::G_ADD, m_Reg(Src0), m_ICst(Cst)));
2364c6eb388SPetar Avramovic   EXPECT_FALSE(match);
2374c6eb388SPetar Avramovic 
2384c6eb388SPetar Avramovic   // Instruction is not binary.
2394c6eb388SPetar Avramovic   match = mi_match(MIBCst, *MRI,
2404c6eb388SPetar Avramovic                    m_BinOp(TargetOpcode::G_MUL, m_Reg(Src0), m_Reg(Src1)));
2414c6eb388SPetar Avramovic   EXPECT_FALSE(match);
2424c6eb388SPetar Avramovic   match = mi_match(MIBUnmerge, *MRI,
2434c6eb388SPetar Avramovic                    m_BinOp(TargetOpcode::G_MUL, m_Reg(Src0), m_Reg(Src1)));
2444c6eb388SPetar Avramovic   EXPECT_FALSE(match);
2454c6eb388SPetar Avramovic 
2464c6eb388SPetar Avramovic   // m_CommutativeBinOp with opcode.
2474c6eb388SPetar Avramovic   match = mi_match(
2484c6eb388SPetar Avramovic       MIBAddCst, *MRI,
2494c6eb388SPetar Avramovic       m_CommutativeBinOp(TargetOpcode::G_ADD, m_ICst(Cst), m_Reg(Src0)));
2504c6eb388SPetar Avramovic   EXPECT_TRUE(match);
2514c6eb388SPetar Avramovic   EXPECT_EQ(Src0, Copies[0]);
2524c6eb388SPetar Avramovic   EXPECT_EQ(Cst, 42);
2534c6eb388SPetar Avramovic 
2544c6eb388SPetar Avramovic   match = mi_match(
2554c6eb388SPetar Avramovic       MIBAddCst, *MRI,
2564c6eb388SPetar Avramovic       m_CommutativeBinOp(TargetOpcode::G_MUL, m_ICst(Cst), m_Reg(Src0)));
2574c6eb388SPetar Avramovic   EXPECT_FALSE(match);
2584c6eb388SPetar Avramovic 
2594c6eb388SPetar Avramovic   match = mi_match(
2604c6eb388SPetar Avramovic       MIBAddCst, *MRI,
2614c6eb388SPetar Avramovic       m_CommutativeBinOp(TargetOpcode::G_ADD, m_Reg(Src0), m_ICst(Cst)));
2624c6eb388SPetar Avramovic   EXPECT_TRUE(match);
2634c6eb388SPetar Avramovic   EXPECT_EQ(Src0, Copies[0]);
2644c6eb388SPetar Avramovic   EXPECT_EQ(Cst, 42);
2654c6eb388SPetar Avramovic 
2664c6eb388SPetar Avramovic   match = mi_match(
2674c6eb388SPetar Avramovic       MIBCst, *MRI,
2684c6eb388SPetar Avramovic       m_CommutativeBinOp(TargetOpcode::G_MUL, m_Reg(Src0), m_Reg(Src1)));
2694c6eb388SPetar Avramovic   EXPECT_FALSE(match);
2704c6eb388SPetar Avramovic   match = mi_match(
2714c6eb388SPetar Avramovic       MIBUnmerge, *MRI,
2724c6eb388SPetar Avramovic       m_CommutativeBinOp(TargetOpcode::G_MUL, m_Reg(Src0), m_Reg(Src1)));
2734c6eb388SPetar Avramovic   EXPECT_FALSE(match);
2742036f446SAditya Nandakumar }
2752036f446SAditya Nandakumar 
TEST_F(AArch64GISelMITest,MatchICmp)27658f843a5SMatt Arsenault TEST_F(AArch64GISelMITest, MatchICmp) {
27742a84d22SDaniel Sanders   setUp();
278c77bbea9SMatt Arsenault   if (!TM)
279c77bbea9SMatt Arsenault     return;
280c77bbea9SMatt Arsenault 
281c77bbea9SMatt Arsenault   const LLT s1 = LLT::scalar(1);
282c77bbea9SMatt Arsenault   auto CmpEq = B.buildICmp(CmpInst::ICMP_EQ, s1, Copies[0], Copies[1]);
283c77bbea9SMatt Arsenault 
284c77bbea9SMatt Arsenault   // Check match any predicate.
285c77bbea9SMatt Arsenault   bool match =
286c77bbea9SMatt Arsenault       mi_match(CmpEq.getReg(0), *MRI, m_GICmp(m_Pred(), m_Reg(), m_Reg()));
287c77bbea9SMatt Arsenault   EXPECT_TRUE(match);
288c77bbea9SMatt Arsenault 
289c77bbea9SMatt Arsenault   // Check we get the predicate and registers.
290c77bbea9SMatt Arsenault   CmpInst::Predicate Pred;
291c77bbea9SMatt Arsenault   Register Reg0;
292c77bbea9SMatt Arsenault   Register Reg1;
293c77bbea9SMatt Arsenault   match = mi_match(CmpEq.getReg(0), *MRI,
294c77bbea9SMatt Arsenault                    m_GICmp(m_Pred(Pred), m_Reg(Reg0), m_Reg(Reg1)));
295c77bbea9SMatt Arsenault   EXPECT_TRUE(match);
296c77bbea9SMatt Arsenault   EXPECT_EQ(CmpInst::ICMP_EQ, Pred);
297c77bbea9SMatt Arsenault   EXPECT_EQ(Copies[0], Reg0);
298c77bbea9SMatt Arsenault   EXPECT_EQ(Copies[1], Reg1);
299c77bbea9SMatt Arsenault }
300c77bbea9SMatt Arsenault 
TEST_F(AArch64GISelMITest,MatchFCmp)30158f843a5SMatt Arsenault TEST_F(AArch64GISelMITest, MatchFCmp) {
30242a84d22SDaniel Sanders   setUp();
303c77bbea9SMatt Arsenault   if (!TM)
304c77bbea9SMatt Arsenault     return;
305c77bbea9SMatt Arsenault 
306c77bbea9SMatt Arsenault   const LLT s1 = LLT::scalar(1);
307c77bbea9SMatt Arsenault   auto CmpEq = B.buildFCmp(CmpInst::FCMP_OEQ, s1, Copies[0], Copies[1]);
308c77bbea9SMatt Arsenault 
309c77bbea9SMatt Arsenault   // Check match any predicate.
310c77bbea9SMatt Arsenault   bool match =
311c77bbea9SMatt Arsenault       mi_match(CmpEq.getReg(0), *MRI, m_GFCmp(m_Pred(), m_Reg(), m_Reg()));
312c77bbea9SMatt Arsenault   EXPECT_TRUE(match);
313c77bbea9SMatt Arsenault 
314c77bbea9SMatt Arsenault   // Check we get the predicate and registers.
315c77bbea9SMatt Arsenault   CmpInst::Predicate Pred;
316c77bbea9SMatt Arsenault   Register Reg0;
317c77bbea9SMatt Arsenault   Register Reg1;
318c77bbea9SMatt Arsenault   match = mi_match(CmpEq.getReg(0), *MRI,
319c77bbea9SMatt Arsenault                    m_GFCmp(m_Pred(Pred), m_Reg(Reg0), m_Reg(Reg1)));
320c77bbea9SMatt Arsenault   EXPECT_TRUE(match);
321c77bbea9SMatt Arsenault   EXPECT_EQ(CmpInst::FCMP_OEQ, Pred);
322c77bbea9SMatt Arsenault   EXPECT_EQ(Copies[0], Reg0);
323c77bbea9SMatt Arsenault   EXPECT_EQ(Copies[1], Reg1);
324c77bbea9SMatt Arsenault }
325c77bbea9SMatt Arsenault 
TEST_F(AArch64GISelMITest,MatchFPUnaryOp)32658f843a5SMatt Arsenault TEST_F(AArch64GISelMITest, MatchFPUnaryOp) {
32742a84d22SDaniel Sanders   setUp();
3282bc42e90SVolkan Keles   if (!TM)
3292bc42e90SVolkan Keles     return;
3302bc42e90SVolkan Keles 
3312bc42e90SVolkan Keles   // Truncate s64 to s32.
3322bc42e90SVolkan Keles   LLT s32 = LLT::scalar(32);
3332bc42e90SVolkan Keles   auto Copy0s32 = B.buildFPTrunc(s32, Copies[0]);
3342bc42e90SVolkan Keles 
3352bc42e90SVolkan Keles   // Match G_FABS.
336cef44a23SAditya Nandakumar   auto MIBFabs = B.buildInstr(TargetOpcode::G_FABS, {s32}, {Copy0s32});
337ff384481SMarcello Maggioni   bool match =
338b482e1bfSJay Foad       mi_match(MIBFabs.getReg(0), *MRI, m_GFabs(m_Reg()));
339b3e86709SMatt Arsenault   EXPECT_TRUE(match);
3402980b019SAditya Nandakumar 
341e3a676e9SMatt Arsenault   Register Src;
342cef44a23SAditya Nandakumar   auto MIBFNeg = B.buildInstr(TargetOpcode::G_FNEG, {s32}, {Copy0s32});
343b482e1bfSJay Foad   match = mi_match(MIBFNeg.getReg(0), *MRI, m_GFNeg(m_Reg(Src)));
344b3e86709SMatt Arsenault   EXPECT_TRUE(match);
345b482e1bfSJay Foad   EXPECT_EQ(Src, Copy0s32.getReg(0));
3462980b019SAditya Nandakumar 
347b482e1bfSJay Foad   match = mi_match(MIBFabs.getReg(0), *MRI, m_GFabs(m_Reg(Src)));
348b3e86709SMatt Arsenault   EXPECT_TRUE(match);
349b482e1bfSJay Foad   EXPECT_EQ(Src, Copy0s32.getReg(0));
35091fc4e09SAditya Nandakumar 
35191fc4e09SAditya Nandakumar   // Build and match FConstant.
35291fc4e09SAditya Nandakumar   auto MIBFCst = B.buildFConstant(s32, .5);
35391fc4e09SAditya Nandakumar   const ConstantFP *TmpFP{};
354b482e1bfSJay Foad   match = mi_match(MIBFCst.getReg(0), *MRI, m_GFCst(TmpFP));
355b3e86709SMatt Arsenault   EXPECT_TRUE(match);
356b3e86709SMatt Arsenault   EXPECT_TRUE(TmpFP);
35791fc4e09SAditya Nandakumar   APFloat APF((float).5);
35891fc4e09SAditya Nandakumar   auto *CFP = ConstantFP::get(Context, APF);
359b3e86709SMatt Arsenault   EXPECT_EQ(CFP, TmpFP);
36091fc4e09SAditya Nandakumar 
36191fc4e09SAditya Nandakumar   // Build double float.
36291fc4e09SAditya Nandakumar   LLT s64 = LLT::scalar(64);
36391fc4e09SAditya Nandakumar   auto MIBFCst64 = B.buildFConstant(s64, .5);
36491fc4e09SAditya Nandakumar   const ConstantFP *TmpFP64{};
365b482e1bfSJay Foad   match = mi_match(MIBFCst64.getReg(0), *MRI, m_GFCst(TmpFP64));
366b3e86709SMatt Arsenault   EXPECT_TRUE(match);
367b3e86709SMatt Arsenault   EXPECT_TRUE(TmpFP64);
36891fc4e09SAditya Nandakumar   APFloat APF64(.5);
36991fc4e09SAditya Nandakumar   auto CFP64 = ConstantFP::get(Context, APF64);
370b3e86709SMatt Arsenault   EXPECT_EQ(CFP64, TmpFP64);
371b3e86709SMatt Arsenault   EXPECT_NE(TmpFP64, TmpFP);
37291fc4e09SAditya Nandakumar 
37391fc4e09SAditya Nandakumar   // Build half float.
37491fc4e09SAditya Nandakumar   LLT s16 = LLT::scalar(16);
37591fc4e09SAditya Nandakumar   auto MIBFCst16 = B.buildFConstant(s16, .5);
37691fc4e09SAditya Nandakumar   const ConstantFP *TmpFP16{};
377b482e1bfSJay Foad   match = mi_match(MIBFCst16.getReg(0), *MRI, m_GFCst(TmpFP16));
378b3e86709SMatt Arsenault   EXPECT_TRUE(match);
379b3e86709SMatt Arsenault   EXPECT_TRUE(TmpFP16);
38091fc4e09SAditya Nandakumar   bool Ignored;
38191fc4e09SAditya Nandakumar   APFloat APF16(.5);
38291fc4e09SAditya Nandakumar   APF16.convert(APFloat::IEEEhalf(), APFloat::rmNearestTiesToEven, &Ignored);
38391fc4e09SAditya Nandakumar   auto CFP16 = ConstantFP::get(Context, APF16);
384b3e86709SMatt Arsenault   EXPECT_EQ(TmpFP16, CFP16);
385b3e86709SMatt Arsenault   EXPECT_NE(TmpFP16, TmpFP);
3862bc42e90SVolkan Keles }
3872bc42e90SVolkan Keles 
TEST_F(AArch64GISelMITest,MatchExtendsTrunc)38858f843a5SMatt Arsenault TEST_F(AArch64GISelMITest, MatchExtendsTrunc) {
38942a84d22SDaniel Sanders   setUp();
3902036f446SAditya Nandakumar   if (!TM)
3912036f446SAditya Nandakumar     return;
392ff384481SMarcello Maggioni 
3932036f446SAditya Nandakumar   LLT s64 = LLT::scalar(64);
3942036f446SAditya Nandakumar   LLT s32 = LLT::scalar(32);
3952036f446SAditya Nandakumar 
3962036f446SAditya Nandakumar   auto MIBTrunc = B.buildTrunc(s32, Copies[0]);
3972036f446SAditya Nandakumar   auto MIBAExt = B.buildAnyExt(s64, MIBTrunc);
3982036f446SAditya Nandakumar   auto MIBZExt = B.buildZExt(s64, MIBTrunc);
3992036f446SAditya Nandakumar   auto MIBSExt = B.buildSExt(s64, MIBTrunc);
400e3a676e9SMatt Arsenault   Register Src0;
4012036f446SAditya Nandakumar   bool match =
402b482e1bfSJay Foad       mi_match(MIBTrunc.getReg(0), *MRI, m_GTrunc(m_Reg(Src0)));
403b3e86709SMatt Arsenault   EXPECT_TRUE(match);
404b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
4052036f446SAditya Nandakumar   match =
406b482e1bfSJay Foad       mi_match(MIBAExt.getReg(0), *MRI, m_GAnyExt(m_Reg(Src0)));
407b3e86709SMatt Arsenault   EXPECT_TRUE(match);
408b482e1bfSJay Foad   EXPECT_EQ(Src0, MIBTrunc.getReg(0));
4092036f446SAditya Nandakumar 
410b482e1bfSJay Foad   match = mi_match(MIBSExt.getReg(0), *MRI, m_GSExt(m_Reg(Src0)));
411b3e86709SMatt Arsenault   EXPECT_TRUE(match);
412b482e1bfSJay Foad   EXPECT_EQ(Src0, MIBTrunc.getReg(0));
4132036f446SAditya Nandakumar 
414b482e1bfSJay Foad   match = mi_match(MIBZExt.getReg(0), *MRI, m_GZExt(m_Reg(Src0)));
415b3e86709SMatt Arsenault   EXPECT_TRUE(match);
416b482e1bfSJay Foad   EXPECT_EQ(Src0, MIBTrunc.getReg(0));
4172036f446SAditya Nandakumar 
4182036f446SAditya Nandakumar   // Match ext(trunc src)
419b482e1bfSJay Foad   match = mi_match(MIBAExt.getReg(0), *MRI,
4202036f446SAditya Nandakumar                    m_GAnyExt(m_GTrunc(m_Reg(Src0))));
421b3e86709SMatt Arsenault   EXPECT_TRUE(match);
422b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
4232036f446SAditya Nandakumar 
424b482e1bfSJay Foad   match = mi_match(MIBSExt.getReg(0), *MRI,
4252036f446SAditya Nandakumar                    m_GSExt(m_GTrunc(m_Reg(Src0))));
426b3e86709SMatt Arsenault   EXPECT_TRUE(match);
427b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
4282036f446SAditya Nandakumar 
429b482e1bfSJay Foad   match = mi_match(MIBZExt.getReg(0), *MRI,
4302036f446SAditya Nandakumar                    m_GZExt(m_GTrunc(m_Reg(Src0))));
431b3e86709SMatt Arsenault   EXPECT_TRUE(match);
432b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
4332036f446SAditya Nandakumar }
4342036f446SAditya Nandakumar 
TEST_F(AArch64GISelMITest,MatchSpecificType)43558f843a5SMatt Arsenault TEST_F(AArch64GISelMITest, MatchSpecificType) {
43642a84d22SDaniel Sanders   setUp();
4372036f446SAditya Nandakumar   if (!TM)
4382036f446SAditya Nandakumar     return;
43902bb1747SVolkan Keles 
44002bb1747SVolkan Keles   // Try to match a 64bit add.
4412036f446SAditya Nandakumar   LLT s64 = LLT::scalar(64);
4422036f446SAditya Nandakumar   LLT s32 = LLT::scalar(32);
4432036f446SAditya Nandakumar   auto MIBAdd = B.buildAdd(s64, Copies[0], Copies[1]);
444b482e1bfSJay Foad   EXPECT_FALSE(mi_match(MIBAdd.getReg(0), *MRI,
4452036f446SAditya Nandakumar                         m_GAdd(m_SpecificType(s32), m_Reg())));
446b482e1bfSJay Foad   EXPECT_TRUE(mi_match(MIBAdd.getReg(0), *MRI,
4472036f446SAditya Nandakumar                        m_GAdd(m_SpecificType(s64), m_Reg())));
44802bb1747SVolkan Keles 
44902bb1747SVolkan Keles   // Try to match the destination type of a bitcast.
450d5e14ba8SSander de Smalen   LLT v2s32 = LLT::fixed_vector(2, 32);
45102bb1747SVolkan Keles   auto MIBCast = B.buildCast(v2s32, Copies[0]);
452b3e86709SMatt Arsenault   EXPECT_TRUE(
453b482e1bfSJay Foad       mi_match(MIBCast.getReg(0), *MRI, m_GBitcast(m_Reg())));
454b3e86709SMatt Arsenault   EXPECT_TRUE(
455b482e1bfSJay Foad       mi_match(MIBCast.getReg(0), *MRI, m_SpecificType(v2s32)));
456b3e86709SMatt Arsenault   EXPECT_TRUE(
457b482e1bfSJay Foad       mi_match(MIBCast.getReg(1), *MRI, m_SpecificType(s64)));
458bab2d3e2SAditya Nandakumar 
459bab2d3e2SAditya Nandakumar   // Build a PTRToInt and INTTOPTR and match and test them.
460bab2d3e2SAditya Nandakumar   LLT PtrTy = LLT::pointer(0, 64);
461bab2d3e2SAditya Nandakumar   auto MIBIntToPtr = B.buildCast(PtrTy, Copies[0]);
462bab2d3e2SAditya Nandakumar   auto MIBPtrToInt = B.buildCast(s64, MIBIntToPtr);
463e3a676e9SMatt Arsenault   Register Src0;
464bab2d3e2SAditya Nandakumar 
465bab2d3e2SAditya Nandakumar   // match the ptrtoint(inttoptr reg)
466b482e1bfSJay Foad   bool match = mi_match(MIBPtrToInt.getReg(0), *MRI,
467bab2d3e2SAditya Nandakumar                         m_GPtrToInt(m_GIntToPtr(m_Reg(Src0))));
468b3e86709SMatt Arsenault   EXPECT_TRUE(match);
469b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
4702036f446SAditya Nandakumar }
4712036f446SAditya Nandakumar 
TEST_F(AArch64GISelMITest,MatchCombinators)47258f843a5SMatt Arsenault TEST_F(AArch64GISelMITest, MatchCombinators) {
47342a84d22SDaniel Sanders   setUp();
4742036f446SAditya Nandakumar   if (!TM)
4752036f446SAditya Nandakumar     return;
476ff384481SMarcello Maggioni 
4772036f446SAditya Nandakumar   LLT s64 = LLT::scalar(64);
4782036f446SAditya Nandakumar   LLT s32 = LLT::scalar(32);
4792036f446SAditya Nandakumar   auto MIBAdd = B.buildAdd(s64, Copies[0], Copies[1]);
480e3a676e9SMatt Arsenault   Register Src0, Src1;
4812036f446SAditya Nandakumar   bool match =
482b482e1bfSJay Foad       mi_match(MIBAdd.getReg(0), *MRI,
4832036f446SAditya Nandakumar                m_all_of(m_SpecificType(s64), m_GAdd(m_Reg(Src0), m_Reg(Src1))));
484b3e86709SMatt Arsenault   EXPECT_TRUE(match);
485b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
486b3e86709SMatt Arsenault   EXPECT_EQ(Src1, Copies[1]);
4872036f446SAditya Nandakumar   // Check for s32 (which should fail).
4882036f446SAditya Nandakumar   match =
489b482e1bfSJay Foad       mi_match(MIBAdd.getReg(0), *MRI,
4902036f446SAditya Nandakumar                m_all_of(m_SpecificType(s32), m_GAdd(m_Reg(Src0), m_Reg(Src1))));
491b3e86709SMatt Arsenault   EXPECT_FALSE(match);
4922036f446SAditya Nandakumar   match =
493b482e1bfSJay Foad       mi_match(MIBAdd.getReg(0), *MRI,
4942036f446SAditya Nandakumar                m_any_of(m_SpecificType(s32), m_GAdd(m_Reg(Src0), m_Reg(Src1))));
495b3e86709SMatt Arsenault   EXPECT_TRUE(match);
496b3e86709SMatt Arsenault   EXPECT_EQ(Src0, Copies[0]);
497b3e86709SMatt Arsenault   EXPECT_EQ(Src1, Copies[1]);
498cf85f311SAditya Nandakumar 
499cf85f311SAditya Nandakumar   // Match a case where none of the predicates hold true.
500cf85f311SAditya Nandakumar   match = mi_match(
501b482e1bfSJay Foad       MIBAdd.getReg(0), *MRI,
502cf85f311SAditya Nandakumar       m_any_of(m_SpecificType(LLT::scalar(16)), m_GSub(m_Reg(), m_Reg())));
503b3e86709SMatt Arsenault   EXPECT_FALSE(match);
5042036f446SAditya Nandakumar }
5055c7fcbdcSAditya Nandakumar 
TEST_F(AArch64GISelMITest,MatchMiscellaneous)50658f843a5SMatt Arsenault TEST_F(AArch64GISelMITest, MatchMiscellaneous) {
50742a84d22SDaniel Sanders   setUp();
5085c7fcbdcSAditya Nandakumar   if (!TM)
5095c7fcbdcSAditya Nandakumar     return;
510ff384481SMarcello Maggioni 
5115c7fcbdcSAditya Nandakumar   LLT s64 = LLT::scalar(64);
5125c7fcbdcSAditya Nandakumar   auto MIBAdd = B.buildAdd(s64, Copies[0], Copies[1]);
513cc90d419SJessica Paquette   Register Reg = MIBAdd.getReg(0);
514cc90d419SJessica Paquette 
515cc90d419SJessica Paquette   // Only one use of Reg.
5165c7fcbdcSAditya Nandakumar   B.buildCast(LLT::pointer(0, 32), MIBAdd);
517cc90d419SJessica Paquette   EXPECT_TRUE(mi_match(Reg, *MRI, m_OneUse(m_GAdd(m_Reg(), m_Reg()))));
518cc90d419SJessica Paquette   EXPECT_TRUE(mi_match(Reg, *MRI, m_OneNonDBGUse(m_GAdd(m_Reg(), m_Reg()))));
519cc90d419SJessica Paquette 
520cc90d419SJessica Paquette   // Add multiple debug uses of Reg.
521bd4dad87SJack Andersen   B.buildInstr(TargetOpcode::DBG_VALUE, {}, {Reg});
522bd4dad87SJack Andersen   B.buildInstr(TargetOpcode::DBG_VALUE, {}, {Reg});
523cc90d419SJessica Paquette 
524cc90d419SJessica Paquette   EXPECT_FALSE(mi_match(Reg, *MRI, m_OneUse(m_GAdd(m_Reg(), m_Reg()))));
525cc90d419SJessica Paquette   EXPECT_TRUE(mi_match(Reg, *MRI, m_OneNonDBGUse(m_GAdd(m_Reg(), m_Reg()))));
526cc90d419SJessica Paquette 
527cc90d419SJessica Paquette   // Multiple non-debug uses of Reg.
5285c7fcbdcSAditya Nandakumar   B.buildCast(LLT::pointer(1, 32), MIBAdd);
529cc90d419SJessica Paquette   EXPECT_FALSE(mi_match(Reg, *MRI, m_OneUse(m_GAdd(m_Reg(), m_Reg()))));
530cc90d419SJessica Paquette   EXPECT_FALSE(mi_match(Reg, *MRI, m_OneNonDBGUse(m_GAdd(m_Reg(), m_Reg()))));
5315c7fcbdcSAditya Nandakumar }
532b184a2ecSJessica Paquette 
TEST_F(AArch64GISelMITest,MatchSpecificConstant)533b184a2ecSJessica Paquette TEST_F(AArch64GISelMITest, MatchSpecificConstant) {
53442a84d22SDaniel Sanders   setUp();
535b184a2ecSJessica Paquette   if (!TM)
536b184a2ecSJessica Paquette     return;
537b184a2ecSJessica Paquette 
538b184a2ecSJessica Paquette   // Basic case: Can we match a G_CONSTANT with a specific value?
539b184a2ecSJessica Paquette   auto FortyTwo = B.buildConstant(LLT::scalar(64), 42);
540b184a2ecSJessica Paquette   EXPECT_TRUE(mi_match(FortyTwo.getReg(0), *MRI, m_SpecificICst(42)));
541b184a2ecSJessica Paquette   EXPECT_FALSE(mi_match(FortyTwo.getReg(0), *MRI, m_SpecificICst(123)));
542b184a2ecSJessica Paquette 
543b184a2ecSJessica Paquette   // Test that this works inside of a more complex pattern.
544b184a2ecSJessica Paquette   LLT s64 = LLT::scalar(64);
545b184a2ecSJessica Paquette   auto MIBAdd = B.buildAdd(s64, Copies[0], FortyTwo);
546b184a2ecSJessica Paquette   EXPECT_TRUE(mi_match(MIBAdd.getReg(2), *MRI, m_SpecificICst(42)));
547b184a2ecSJessica Paquette 
548b184a2ecSJessica Paquette   // Wrong constant.
549b184a2ecSJessica Paquette   EXPECT_FALSE(mi_match(MIBAdd.getReg(2), *MRI, m_SpecificICst(123)));
550b184a2ecSJessica Paquette 
551b184a2ecSJessica Paquette   // No constant on the LHS.
552b184a2ecSJessica Paquette   EXPECT_FALSE(mi_match(MIBAdd.getReg(1), *MRI, m_SpecificICst(42)));
553b184a2ecSJessica Paquette }
554b184a2ecSJessica Paquette 
TEST_F(AArch64GISelMITest,MatchSpecificConstantSplat)555bc5dbb0bSAbinav Puthan Purayil TEST_F(AArch64GISelMITest, MatchSpecificConstantSplat) {
556bc5dbb0bSAbinav Puthan Purayil   setUp();
557bc5dbb0bSAbinav Puthan Purayil   if (!TM)
558bc5dbb0bSAbinav Puthan Purayil     return;
559bc5dbb0bSAbinav Puthan Purayil 
560bc5dbb0bSAbinav Puthan Purayil   LLT s64 = LLT::scalar(64);
561bc5dbb0bSAbinav Puthan Purayil   LLT v4s64 = LLT::fixed_vector(4, s64);
562bc5dbb0bSAbinav Puthan Purayil 
563bc5dbb0bSAbinav Puthan Purayil   MachineInstrBuilder FortyTwoSplat =
564bc5dbb0bSAbinav Puthan Purayil       B.buildSplatVector(v4s64, B.buildConstant(s64, 42));
565bc5dbb0bSAbinav Puthan Purayil   MachineInstrBuilder FortyTwo = B.buildConstant(s64, 42);
566bc5dbb0bSAbinav Puthan Purayil 
567bc5dbb0bSAbinav Puthan Purayil   EXPECT_TRUE(mi_match(FortyTwoSplat.getReg(0), *MRI, m_SpecificICstSplat(42)));
568bc5dbb0bSAbinav Puthan Purayil   EXPECT_FALSE(
569bc5dbb0bSAbinav Puthan Purayil       mi_match(FortyTwoSplat.getReg(0), *MRI, m_SpecificICstSplat(43)));
570bc5dbb0bSAbinav Puthan Purayil   EXPECT_FALSE(mi_match(FortyTwo.getReg(0), *MRI, m_SpecificICstSplat(42)));
571bc5dbb0bSAbinav Puthan Purayil 
572bc5dbb0bSAbinav Puthan Purayil   MachineInstrBuilder NonConstantSplat =
573bc5dbb0bSAbinav Puthan Purayil       B.buildBuildVector(v4s64, {Copies[0], Copies[0], Copies[0], Copies[0]});
574bc5dbb0bSAbinav Puthan Purayil 
575bc5dbb0bSAbinav Puthan Purayil   MachineInstrBuilder AddSplat =
576bc5dbb0bSAbinav Puthan Purayil       B.buildAdd(v4s64, NonConstantSplat, FortyTwoSplat);
577bc5dbb0bSAbinav Puthan Purayil   EXPECT_TRUE(mi_match(AddSplat.getReg(2), *MRI, m_SpecificICstSplat(42)));
578bc5dbb0bSAbinav Puthan Purayil   EXPECT_FALSE(mi_match(AddSplat.getReg(2), *MRI, m_SpecificICstSplat(43)));
579bc5dbb0bSAbinav Puthan Purayil   EXPECT_FALSE(mi_match(AddSplat.getReg(1), *MRI, m_SpecificICstSplat(42)));
580bc5dbb0bSAbinav Puthan Purayil 
581bc5dbb0bSAbinav Puthan Purayil   MachineInstrBuilder Add = B.buildAdd(s64, Copies[0], FortyTwo);
582bc5dbb0bSAbinav Puthan Purayil   EXPECT_FALSE(mi_match(Add.getReg(2), *MRI, m_SpecificICstSplat(42)));
583bc5dbb0bSAbinav Puthan Purayil }
584bc5dbb0bSAbinav Puthan Purayil 
TEST_F(AArch64GISelMITest,MatchSpecificConstantOrSplat)585bc5dbb0bSAbinav Puthan Purayil TEST_F(AArch64GISelMITest, MatchSpecificConstantOrSplat) {
586bc5dbb0bSAbinav Puthan Purayil   setUp();
587bc5dbb0bSAbinav Puthan Purayil   if (!TM)
588bc5dbb0bSAbinav Puthan Purayil     return;
589bc5dbb0bSAbinav Puthan Purayil 
590bc5dbb0bSAbinav Puthan Purayil   LLT s64 = LLT::scalar(64);
591bc5dbb0bSAbinav Puthan Purayil   LLT v4s64 = LLT::fixed_vector(4, s64);
592bc5dbb0bSAbinav Puthan Purayil 
593bc5dbb0bSAbinav Puthan Purayil   MachineInstrBuilder FortyTwoSplat =
594bc5dbb0bSAbinav Puthan Purayil       B.buildSplatVector(v4s64, B.buildConstant(s64, 42));
595bc5dbb0bSAbinav Puthan Purayil   MachineInstrBuilder FortyTwo = B.buildConstant(s64, 42);
596bc5dbb0bSAbinav Puthan Purayil 
597bc5dbb0bSAbinav Puthan Purayil   EXPECT_TRUE(
598bc5dbb0bSAbinav Puthan Purayil       mi_match(FortyTwoSplat.getReg(0), *MRI, m_SpecificICstOrSplat(42)));
599bc5dbb0bSAbinav Puthan Purayil   EXPECT_FALSE(
600bc5dbb0bSAbinav Puthan Purayil       mi_match(FortyTwoSplat.getReg(0), *MRI, m_SpecificICstOrSplat(43)));
601bc5dbb0bSAbinav Puthan Purayil   EXPECT_TRUE(mi_match(FortyTwo.getReg(0), *MRI, m_SpecificICstOrSplat(42)));
602bc5dbb0bSAbinav Puthan Purayil 
603bc5dbb0bSAbinav Puthan Purayil   MachineInstrBuilder NonConstantSplat =
604bc5dbb0bSAbinav Puthan Purayil       B.buildBuildVector(v4s64, {Copies[0], Copies[0], Copies[0], Copies[0]});
605bc5dbb0bSAbinav Puthan Purayil 
606bc5dbb0bSAbinav Puthan Purayil   MachineInstrBuilder AddSplat =
607bc5dbb0bSAbinav Puthan Purayil       B.buildAdd(v4s64, NonConstantSplat, FortyTwoSplat);
608bc5dbb0bSAbinav Puthan Purayil   EXPECT_TRUE(mi_match(AddSplat.getReg(2), *MRI, m_SpecificICstOrSplat(42)));
609bc5dbb0bSAbinav Puthan Purayil   EXPECT_FALSE(mi_match(AddSplat.getReg(2), *MRI, m_SpecificICstOrSplat(43)));
610bc5dbb0bSAbinav Puthan Purayil   EXPECT_FALSE(mi_match(AddSplat.getReg(1), *MRI, m_SpecificICstOrSplat(42)));
611bc5dbb0bSAbinav Puthan Purayil 
612bc5dbb0bSAbinav Puthan Purayil   MachineInstrBuilder Add = B.buildAdd(s64, Copies[0], FortyTwo);
613bc5dbb0bSAbinav Puthan Purayil   EXPECT_TRUE(mi_match(Add.getReg(2), *MRI, m_SpecificICstOrSplat(42)));
614bc5dbb0bSAbinav Puthan Purayil }
615bc5dbb0bSAbinav Puthan Purayil 
TEST_F(AArch64GISelMITest,MatchZeroInt)616b184a2ecSJessica Paquette TEST_F(AArch64GISelMITest, MatchZeroInt) {
61742a84d22SDaniel Sanders   setUp();
618b184a2ecSJessica Paquette   if (!TM)
619b184a2ecSJessica Paquette     return;
620b184a2ecSJessica Paquette   auto Zero = B.buildConstant(LLT::scalar(64), 0);
621b184a2ecSJessica Paquette   EXPECT_TRUE(mi_match(Zero.getReg(0), *MRI, m_ZeroInt()));
622b184a2ecSJessica Paquette 
623b184a2ecSJessica Paquette   auto FortyTwo = B.buildConstant(LLT::scalar(64), 42);
624b184a2ecSJessica Paquette   EXPECT_FALSE(mi_match(FortyTwo.getReg(0), *MRI, m_ZeroInt()));
625b184a2ecSJessica Paquette }
626b184a2ecSJessica Paquette 
TEST_F(AArch64GISelMITest,MatchAllOnesInt)627d6a88e7eSJessica Paquette TEST_F(AArch64GISelMITest, MatchAllOnesInt) {
62842a84d22SDaniel Sanders   setUp();
629d6a88e7eSJessica Paquette   if (!TM)
630d6a88e7eSJessica Paquette     return;
631d6a88e7eSJessica Paquette   auto AllOnes = B.buildConstant(LLT::scalar(64), -1);
632d6a88e7eSJessica Paquette   EXPECT_TRUE(mi_match(AllOnes.getReg(0), *MRI, m_AllOnesInt()));
633d6a88e7eSJessica Paquette 
634d6a88e7eSJessica Paquette   auto FortyTwo = B.buildConstant(LLT::scalar(64), 42);
635d6a88e7eSJessica Paquette   EXPECT_FALSE(mi_match(FortyTwo.getReg(0), *MRI, m_AllOnesInt()));
636d6a88e7eSJessica Paquette }
637d6a88e7eSJessica Paquette 
TEST_F(AArch64GISelMITest,MatchFPOrIntConst)638d477a7c2SPetar Avramovic TEST_F(AArch64GISelMITest, MatchFPOrIntConst) {
639d477a7c2SPetar Avramovic   setUp();
640d477a7c2SPetar Avramovic   if (!TM)
641d477a7c2SPetar Avramovic     return;
642d477a7c2SPetar Avramovic 
643d477a7c2SPetar Avramovic   Register IntOne = B.buildConstant(LLT::scalar(64), 1).getReg(0);
644d477a7c2SPetar Avramovic   Register FPOne = B.buildFConstant(LLT::scalar(64), 1.0).getReg(0);
645d477a7c2SPetar Avramovic   Optional<ValueAndVReg> ValReg;
646d477a7c2SPetar Avramovic   Optional<FPValueAndVReg> FValReg;
647d477a7c2SPetar Avramovic 
648d477a7c2SPetar Avramovic   EXPECT_TRUE(mi_match(IntOne, *MRI, m_GCst(ValReg)));
649d477a7c2SPetar Avramovic   EXPECT_EQ(IntOne, ValReg->VReg);
650d477a7c2SPetar Avramovic   EXPECT_FALSE(mi_match(IntOne, *MRI, m_GFCst(FValReg)));
651d477a7c2SPetar Avramovic 
652d477a7c2SPetar Avramovic   EXPECT_FALSE(mi_match(FPOne, *MRI, m_GCst(ValReg)));
653d477a7c2SPetar Avramovic   EXPECT_TRUE(mi_match(FPOne, *MRI, m_GFCst(FValReg)));
654d477a7c2SPetar Avramovic   EXPECT_EQ(FPOne, FValReg->VReg);
655d477a7c2SPetar Avramovic }
656d477a7c2SPetar Avramovic 
TEST_F(AArch64GISelMITest,MatchConstantSplat)6578bc71856SPetar Avramovic TEST_F(AArch64GISelMITest, MatchConstantSplat) {
6588bc71856SPetar Avramovic   setUp();
6598bc71856SPetar Avramovic   if (!TM)
6608bc71856SPetar Avramovic     return;
6618bc71856SPetar Avramovic 
6628bc71856SPetar Avramovic   LLT s64 = LLT::scalar(64);
6638bc71856SPetar Avramovic   LLT v4s64 = LLT::fixed_vector(4, 64);
6648bc71856SPetar Avramovic 
6658bc71856SPetar Avramovic   Register FPOne = B.buildFConstant(s64, 1.0).getReg(0);
6668bc71856SPetar Avramovic   Register FPZero = B.buildFConstant(s64, 0.0).getReg(0);
6678bc71856SPetar Avramovic   Register Undef = B.buildUndef(s64).getReg(0);
6688bc71856SPetar Avramovic   Optional<FPValueAndVReg> FValReg;
6698bc71856SPetar Avramovic 
6708bc71856SPetar Avramovic   // GFCstOrSplatGFCstMatch allows undef as part of splat. Undef often comes
6718bc71856SPetar Avramovic   // from padding to legalize into available operation and then ignore added
6728bc71856SPetar Avramovic   // elements e.g. v3s64 to v4s64.
6738bc71856SPetar Avramovic 
6748bc71856SPetar Avramovic   EXPECT_TRUE(mi_match(FPZero, *MRI, GFCstOrSplatGFCstMatch(FValReg)));
6758bc71856SPetar Avramovic   EXPECT_EQ(FPZero, FValReg->VReg);
6768bc71856SPetar Avramovic 
6778bc71856SPetar Avramovic   EXPECT_FALSE(mi_match(Undef, *MRI, GFCstOrSplatGFCstMatch(FValReg)));
6788bc71856SPetar Avramovic 
6798bc71856SPetar Avramovic   auto ZeroSplat = B.buildBuildVector(v4s64, {FPZero, FPZero, FPZero, FPZero});
6808bc71856SPetar Avramovic   EXPECT_TRUE(
6818bc71856SPetar Avramovic       mi_match(ZeroSplat.getReg(0), *MRI, GFCstOrSplatGFCstMatch(FValReg)));
6828bc71856SPetar Avramovic   EXPECT_EQ(FPZero, FValReg->VReg);
6838bc71856SPetar Avramovic 
6848bc71856SPetar Avramovic   auto ZeroUndef = B.buildBuildVector(v4s64, {FPZero, FPZero, FPZero, Undef});
6858bc71856SPetar Avramovic   EXPECT_TRUE(
6868bc71856SPetar Avramovic       mi_match(ZeroUndef.getReg(0), *MRI, GFCstOrSplatGFCstMatch(FValReg)));
6878bc71856SPetar Avramovic   EXPECT_EQ(FPZero, FValReg->VReg);
6888bc71856SPetar Avramovic 
6898bc71856SPetar Avramovic   // All undefs are not constant splat.
6908bc71856SPetar Avramovic   auto UndefSplat = B.buildBuildVector(v4s64, {Undef, Undef, Undef, Undef});
6918bc71856SPetar Avramovic   EXPECT_FALSE(
6928bc71856SPetar Avramovic       mi_match(UndefSplat.getReg(0), *MRI, GFCstOrSplatGFCstMatch(FValReg)));
6938bc71856SPetar Avramovic 
6948bc71856SPetar Avramovic   auto ZeroOne = B.buildBuildVector(v4s64, {FPZero, FPZero, FPZero, FPOne});
6958bc71856SPetar Avramovic   EXPECT_FALSE(
6968bc71856SPetar Avramovic       mi_match(ZeroOne.getReg(0), *MRI, GFCstOrSplatGFCstMatch(FValReg)));
6978bc71856SPetar Avramovic 
6988bc71856SPetar Avramovic   auto NonConstantSplat =
6998bc71856SPetar Avramovic       B.buildBuildVector(v4s64, {Copies[0], Copies[0], Copies[0], Copies[0]});
7008bc71856SPetar Avramovic   EXPECT_FALSE(mi_match(NonConstantSplat.getReg(0), *MRI,
7018bc71856SPetar Avramovic                         GFCstOrSplatGFCstMatch(FValReg)));
7028bc71856SPetar Avramovic 
7038bc71856SPetar Avramovic   auto Mixed = B.buildBuildVector(v4s64, {FPZero, FPZero, FPZero, Copies[0]});
7048bc71856SPetar Avramovic   EXPECT_FALSE(
7058bc71856SPetar Avramovic       mi_match(Mixed.getReg(0), *MRI, GFCstOrSplatGFCstMatch(FValReg)));
7068bc71856SPetar Avramovic }
7078bc71856SPetar Avramovic 
TEST_F(AArch64GISelMITest,MatchNeg)708b184a2ecSJessica Paquette TEST_F(AArch64GISelMITest, MatchNeg) {
70942a84d22SDaniel Sanders   setUp();
710b184a2ecSJessica Paquette   if (!TM)
711b184a2ecSJessica Paquette     return;
712b184a2ecSJessica Paquette 
713b184a2ecSJessica Paquette   LLT s64 = LLT::scalar(64);
714b184a2ecSJessica Paquette   auto Zero = B.buildConstant(LLT::scalar(64), 0);
715b184a2ecSJessica Paquette   auto NegInst = B.buildSub(s64, Zero, Copies[0]);
716b184a2ecSJessica Paquette   Register NegatedReg;
717b184a2ecSJessica Paquette 
718b184a2ecSJessica Paquette   // Match: G_SUB = 0, %Reg
719b184a2ecSJessica Paquette   EXPECT_TRUE(mi_match(NegInst.getReg(0), *MRI, m_Neg(m_Reg(NegatedReg))));
720b184a2ecSJessica Paquette   EXPECT_EQ(NegatedReg, Copies[0]);
721b184a2ecSJessica Paquette 
722b184a2ecSJessica Paquette   // Don't match: G_SUB = %Reg, 0
723b184a2ecSJessica Paquette   auto NotNegInst1 = B.buildSub(s64, Copies[0], Zero);
724b184a2ecSJessica Paquette   EXPECT_FALSE(mi_match(NotNegInst1.getReg(0), *MRI, m_Neg(m_Reg(NegatedReg))));
725b184a2ecSJessica Paquette 
726b184a2ecSJessica Paquette   // Don't match: G_SUB = 42, %Reg
727b184a2ecSJessica Paquette   auto FortyTwo = B.buildConstant(LLT::scalar(64), 42);
728b184a2ecSJessica Paquette   auto NotNegInst2 = B.buildSub(s64, FortyTwo, Copies[0]);
729b184a2ecSJessica Paquette   EXPECT_FALSE(mi_match(NotNegInst2.getReg(0), *MRI, m_Neg(m_Reg(NegatedReg))));
730b184a2ecSJessica Paquette 
731b184a2ecSJessica Paquette   // Complex testcase.
732b184a2ecSJessica Paquette   // %sub = G_SUB = 0, %negated_reg
733b184a2ecSJessica Paquette   // %add = G_ADD = %x, %sub
734b184a2ecSJessica Paquette   auto AddInst = B.buildAdd(s64, Copies[1], NegInst);
735b184a2ecSJessica Paquette   NegatedReg = Register();
736b184a2ecSJessica Paquette   EXPECT_TRUE(mi_match(AddInst.getReg(2), *MRI, m_Neg(m_Reg(NegatedReg))));
737b184a2ecSJessica Paquette   EXPECT_EQ(NegatedReg, Copies[0]);
738b184a2ecSJessica Paquette }
739d6a88e7eSJessica Paquette 
TEST_F(AArch64GISelMITest,MatchNot)740d6a88e7eSJessica Paquette TEST_F(AArch64GISelMITest, MatchNot) {
74142a84d22SDaniel Sanders   setUp();
742d6a88e7eSJessica Paquette   if (!TM)
743d6a88e7eSJessica Paquette     return;
744d6a88e7eSJessica Paquette 
745d6a88e7eSJessica Paquette   LLT s64 = LLT::scalar(64);
746d6a88e7eSJessica Paquette   auto AllOnes = B.buildConstant(LLT::scalar(64), -1);
747d6a88e7eSJessica Paquette   auto NotInst1 = B.buildXor(s64, Copies[0], AllOnes);
748d6a88e7eSJessica Paquette   Register NotReg;
749d6a88e7eSJessica Paquette 
750d6a88e7eSJessica Paquette   // Match: G_XOR %NotReg, -1
751d6a88e7eSJessica Paquette   EXPECT_TRUE(mi_match(NotInst1.getReg(0), *MRI, m_Not(m_Reg(NotReg))));
752d6a88e7eSJessica Paquette   EXPECT_EQ(NotReg, Copies[0]);
753d6a88e7eSJessica Paquette 
754d6a88e7eSJessica Paquette   // Match: G_XOR -1, %NotReg
755d6a88e7eSJessica Paquette   auto NotInst2 = B.buildXor(s64, AllOnes, Copies[1]);
756d6a88e7eSJessica Paquette   EXPECT_TRUE(mi_match(NotInst2.getReg(0), *MRI, m_Not(m_Reg(NotReg))));
757d6a88e7eSJessica Paquette   EXPECT_EQ(NotReg, Copies[1]);
758d6a88e7eSJessica Paquette 
759d6a88e7eSJessica Paquette   // Don't match: G_XOR %NotReg, 42
760d6a88e7eSJessica Paquette   auto FortyTwo = B.buildConstant(LLT::scalar(64), 42);
761d6a88e7eSJessica Paquette   auto WrongCst = B.buildXor(s64, Copies[0], FortyTwo);
762d6a88e7eSJessica Paquette   EXPECT_FALSE(mi_match(WrongCst.getReg(0), *MRI, m_Not(m_Reg(NotReg))));
763d6a88e7eSJessica Paquette 
764d6a88e7eSJessica Paquette   // Complex testcase.
765d6a88e7eSJessica Paquette   // %xor = G_XOR %NotReg, -1
766d6a88e7eSJessica Paquette   // %add = G_ADD %x, %xor
767d6a88e7eSJessica Paquette   auto AddInst = B.buildAdd(s64, Copies[1], NotInst1);
768d6a88e7eSJessica Paquette   NotReg = Register();
769d6a88e7eSJessica Paquette   EXPECT_TRUE(mi_match(AddInst.getReg(2), *MRI, m_Not(m_Reg(NotReg))));
770d6a88e7eSJessica Paquette   EXPECT_EQ(NotReg, Copies[0]);
771d6a88e7eSJessica Paquette }
7722036f446SAditya Nandakumar } // namespace
7732036f446SAditya Nandakumar 
main(int argc,char ** argv)7742036f446SAditya Nandakumar int main(int argc, char **argv) {
7752036f446SAditya Nandakumar   ::testing::InitGoogleTest(&argc, argv);
7762036f446SAditya Nandakumar   initLLVM();
7772036f446SAditya Nandakumar   return RUN_ALL_TESTS();
7782036f446SAditya Nandakumar }
779