llvm.org GIT mirror llvm / 30635bc
[ValueTracking] Allow select patterns to work on FP vectors Summary: This CL allows constant vectors of floats to be recognized as non-NaN and non-zero in select patterns. This change makes `matchSelectPattern` more powerful generally, but was motivated specifically because I wanted fminnan and fmaxnan to be created for vector versions of the scalar patterns they are created for. Tested with check-all on all targets. A testcase in the WebAssembly backend that tests the non-nan codepath is in an upcoming CL. Reviewers: aheejin, dschuff Subscribers: sunfish, llvm-commits Differential Revision: https://reviews.llvm.org/D52324 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@343364 91177308-0d34-0410-b5e6-96231b3b80d8 Thomas Lively 11 months ago
2 changed file(s) with 80 addition(s) and 0 deletion(s). Raw diff Collapse all Expand all
43964396
43974397 if (auto *C = dyn_cast(V))
43984398 return !C->isNaN();
4399
4400 if (auto *C = dyn_cast(V)) {
4401 if (!C->getElementType()->isFloatingPointTy())
4402 return false;
4403 for (unsigned I = 0, E = C->getNumElements(); I < E; ++I) {
4404 if (C->getElementAsAPFloat(I).isNaN())
4405 return false;
4406 }
4407 return true;
4408 }
4409
43994410 return false;
44004411 }
44014412
44024413 static bool isKnownNonZero(const Value *V) {
44034414 if (auto *C = dyn_cast(V))
44044415 return !C->isZero();
4416
4417 if (auto *C = dyn_cast(V)) {
4418 if (!C->getElementType()->isFloatingPointTy())
4419 return false;
4420 for (unsigned I = 0, E = C->getNumElements(); I < E; ++I) {
4421 if (C->getElementAsAPFloat(I).isZero())
4422 return false;
4423 }
4424 return true;
4425 }
4426
44054427 return false;
44064428 }
44074429
146146 "}\n");
147147 // But this should be, because we've ignored signed zeroes.
148148 expectPattern({SPF_FMINNUM, SPNB_RETURNS_OTHER, true});
149 }
150
151 TEST_F(MatchSelectPatternTest, VectorFMinNaN) {
152 parseAssembly(
153 "define <4 x float> @test(<4 x float> %a) {\n"
154 " %1 = fcmp ule <4 x float> %a, \n"
155 " \n"
156 " %A = select <4 x i1> %1, <4 x float> %a,\n"
157 " <4 x float> \n"
158 " ret <4 x float> %A\n"
159 "}\n");
160 // Check that pattern matching works on vectors where each lane has the same
161 // unordered pattern.
162 expectPattern({SPF_FMINNUM, SPNB_RETURNS_NAN, false});
163 }
164
165 TEST_F(MatchSelectPatternTest, VectorFMinOtherOrdered) {
166 parseAssembly(
167 "define <4 x float> @test(<4 x float> %a) {\n"
168 " %1 = fcmp ole <4 x float> %a, \n"
169 " \n"
170 " %A = select <4 x i1> %1, <4 x float> %a,\n"
171 " <4 x float> \n"
172 " ret <4 x float> %A\n"
173 "}\n");
174 // Check that pattern matching works on vectors where each lane has the same
175 // ordered pattern.
176 expectPattern({SPF_FMINNUM, SPNB_RETURNS_OTHER, true});
177 }
178
179 TEST_F(MatchSelectPatternTest, VectorNotFMinNaN) {
180 parseAssembly(
181 "define <4 x float> @test(<4 x float> %a) {\n"
182 " %1 = fcmp ule <4 x float> %a, \n"
183 " \n"
184 " %A = select <4 x i1> %1, <4 x float> %a,\n"
185 " <4 x float>
186 "5.0>\n"
187 " ret <4 x float> %A\n"
188 "}\n");
189 // The lane that contains a NaN (0x7ff80...) behaves like a
190 // non-NaN-propagating min and the other lines behave like a NaN-propagating
191 // min, so check that neither is returned.
192 expectPattern({SPF_UNKNOWN, SPNB_NA, false});
193 }
194
195 TEST_F(MatchSelectPatternTest, VectorNotFMinZero) {
196 parseAssembly(
197 "define <4 x float> @test(<4 x float> %a) {\n"
198 " %1 = fcmp ule <4 x float> %a, \n"
199 " \n"
200 " %A = select <4 x i1> %1, <4 x float> %a,\n"
201 " <4 x float> \n"
202 " ret <4 x float> %A\n"
203 "}\n");
204 // Always selects the second lane of %a if it is positive or negative zero, so
205 // this is stricter than a min.
206 expectPattern({SPF_UNKNOWN, SPNB_NA, false});
149207 }
150208
151209 TEST_F(MatchSelectPatternTest, DoubleCastU) {