1; RUN: llc < %s -march=x86-64 -asm-verbose=false -join-physregs -promote-elements | FileCheck %s 2; RUN: llc < %s -march=x86-64 -asm-verbose=false -join-physregs -enable-unsafe-fp-math -enable-no-nans-fp-math -promote-elements | FileCheck -check-prefix=UNSAFE %s 3; RUN: llc < %s -march=x86-64 -asm-verbose=false -join-physregs -enable-no-nans-fp-math -promote-elements | FileCheck -check-prefix=FINITE %s 4 5; Some of these patterns can be matched as SSE min or max. Some of 6; then can be matched provided that the operands are swapped. 7; Some of them can't be matched at all and require a comparison 8; and a conditional branch. 9 10; The naming convention is {,x_,y_}{o,u}{gt,lt,ge,le}{,_inverse} 11; x_ : use 0.0 instead of %y 12; y_ : use -0.0 instead of %y 13; _inverse : swap the arms of the select. 14 15; Some of these tests depend on -join-physregs commuting instructions to 16; eliminate copies. 17 18; CHECK: ogt: 19; CHECK-NEXT: maxsd %xmm1, %xmm0 20; CHECK-NEXT: ret 21; UNSAFE: ogt: 22; UNSAFE-NEXT: maxsd %xmm1, %xmm0 23; UNSAFE-NEXT: ret 24; FINITE: ogt: 25; FINITE-NEXT: maxsd %xmm1, %xmm0 26; FINITE-NEXT: ret 27define double @ogt(double %x, double %y) nounwind { 28 %c = fcmp ogt double %x, %y 29 %d = select i1 %c, double %x, double %y 30 ret double %d 31} 32 33; CHECK: olt: 34; CHECK-NEXT: minsd %xmm1, %xmm0 35; CHECK-NEXT: ret 36; UNSAFE: olt: 37; UNSAFE-NEXT: minsd %xmm1, %xmm0 38; UNSAFE-NEXT: ret 39; FINITE: olt: 40; FINITE-NEXT: minsd %xmm1, %xmm0 41; FINITE-NEXT: ret 42define double @olt(double %x, double %y) nounwind { 43 %c = fcmp olt double %x, %y 44 %d = select i1 %c, double %x, double %y 45 ret double %d 46} 47 48; CHECK: ogt_inverse: 49; CHECK-NEXT: minsd %xmm0, %xmm1 50; CHECK-NEXT: movap{{[sd]}} %xmm1, %xmm0 51; CHECK-NEXT: ret 52; UNSAFE: ogt_inverse: 53; UNSAFE-NEXT: minsd %xmm0, %xmm1 54; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 55; UNSAFE-NEXT: ret 56; FINITE: ogt_inverse: 57; FINITE-NEXT: minsd %xmm0, %xmm1 58; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 59; FINITE-NEXT: ret 60define double @ogt_inverse(double %x, double %y) nounwind { 61 %c = fcmp ogt double %x, %y 62 %d = select i1 %c, double %y, double %x 63 ret double %d 64} 65 66; CHECK: olt_inverse: 67; CHECK-NEXT: maxsd %xmm0, %xmm1 68; CHECK-NEXT: movap{{[sd]}} %xmm1, %xmm0 69; CHECK-NEXT: ret 70; UNSAFE: olt_inverse: 71; UNSAFE-NEXT: maxsd %xmm0, %xmm1 72; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 73; UNSAFE-NEXT: ret 74; FINITE: olt_inverse: 75; FINITE-NEXT: maxsd %xmm0, %xmm1 76; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 77; FINITE-NEXT: ret 78define double @olt_inverse(double %x, double %y) nounwind { 79 %c = fcmp olt double %x, %y 80 %d = select i1 %c, double %y, double %x 81 ret double %d 82} 83 84; CHECK: oge: 85; CHECK-NEXT: ucomisd %xmm1, %xmm0 86; UNSAFE: oge: 87; UNSAFE-NEXT: maxsd %xmm1, %xmm0 88; UNSAFE-NEXT: ret 89; FINITE: oge: 90; FINITE-NEXT: maxsd %xmm1, %xmm0 91; FINITE-NEXT: ret 92define double @oge(double %x, double %y) nounwind { 93 %c = fcmp oge double %x, %y 94 %d = select i1 %c, double %x, double %y 95 ret double %d 96} 97 98; CHECK: ole: 99; CHECK-NEXT: ucomisd %xmm0, %xmm1 100; UNSAFE: ole: 101; UNSAFE-NEXT: minsd %xmm1, %xmm0 102; FINITE: ole: 103; FINITE-NEXT: minsd %xmm1, %xmm0 104define double @ole(double %x, double %y) nounwind { 105 %c = fcmp ole double %x, %y 106 %d = select i1 %c, double %x, double %y 107 ret double %d 108} 109 110; CHECK: oge_inverse: 111; CHECK-NEXT: ucomisd %xmm1, %xmm0 112; UNSAFE: oge_inverse: 113; UNSAFE-NEXT: minsd %xmm0, %xmm1 114; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 115; UNSAFE-NEXT: ret 116; FINITE: oge_inverse: 117; FINITE-NEXT: minsd %xmm0, %xmm1 118; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 119; FINITE-NEXT: ret 120define double @oge_inverse(double %x, double %y) nounwind { 121 %c = fcmp oge double %x, %y 122 %d = select i1 %c, double %y, double %x 123 ret double %d 124} 125 126; CHECK: ole_inverse: 127; CHECK-NEXT: ucomisd %xmm0, %xmm1 128; UNSAFE: ole_inverse: 129; UNSAFE-NEXT: maxsd %xmm0, %xmm1 130; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 131; UNSAFE-NEXT: ret 132; FINITE: ole_inverse: 133; FINITE-NEXT: maxsd %xmm0, %xmm1 134; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 135; FINITE-NEXT: ret 136define double @ole_inverse(double %x, double %y) nounwind { 137 %c = fcmp ole double %x, %y 138 %d = select i1 %c, double %y, double %x 139 ret double %d 140} 141 142; CHECK: x_ogt: 143; CHECK-NEXT: xorp{{[sd]}} %xmm1, %xmm1 144; CHECK-NEXT: maxsd %xmm1, %xmm0 145; CHECK-NEXT: ret 146; UNSAFE: x_ogt: 147; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 148; UNSAFE-NEXT: maxsd %xmm1, %xmm0 149; UNSAFE-NEXT: ret 150; FINITE: x_ogt: 151; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 152; FINITE-NEXT: maxsd %xmm1, %xmm0 153; FINITE-NEXT: ret 154define double @x_ogt(double %x) nounwind { 155 %c = fcmp ogt double %x, 0.000000e+00 156 %d = select i1 %c, double %x, double 0.000000e+00 157 ret double %d 158} 159 160; CHECK: x_olt: 161; CHECK-NEXT: xorp{{[sd]}} %xmm1, %xmm1 162; CHECK-NEXT: minsd %xmm1, %xmm0 163; CHECK-NEXT: ret 164; UNSAFE: x_olt: 165; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 166; UNSAFE-NEXT: minsd %xmm1, %xmm0 167; UNSAFE-NEXT: ret 168; FINITE: x_olt: 169; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 170; FINITE-NEXT: minsd %xmm1, %xmm0 171; FINITE-NEXT: ret 172define double @x_olt(double %x) nounwind { 173 %c = fcmp olt double %x, 0.000000e+00 174 %d = select i1 %c, double %x, double 0.000000e+00 175 ret double %d 176} 177 178; CHECK: x_ogt_inverse: 179; CHECK-NEXT: xorp{{[sd]}} %xmm1, %xmm1 180; CHECK-NEXT: minsd %xmm0, %xmm1 181; CHECK-NEXT: movap{{[sd]}} %xmm1, %xmm0 182; CHECK-NEXT: ret 183; UNSAFE: x_ogt_inverse: 184; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 185; UNSAFE-NEXT: minsd %xmm0, %xmm1 186; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 187; UNSAFE-NEXT: ret 188; FINITE: x_ogt_inverse: 189; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 190; FINITE-NEXT: minsd %xmm0, %xmm1 191; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 192; FINITE-NEXT: ret 193define double @x_ogt_inverse(double %x) nounwind { 194 %c = fcmp ogt double %x, 0.000000e+00 195 %d = select i1 %c, double 0.000000e+00, double %x 196 ret double %d 197} 198 199; CHECK: x_olt_inverse: 200; CHECK-NEXT: xorp{{[sd]}} %xmm1, %xmm1 201; CHECK-NEXT: maxsd %xmm0, %xmm1 202; CHECK-NEXT: movap{{[sd]}} %xmm1, %xmm0 203; CHECK-NEXT: ret 204; UNSAFE: x_olt_inverse: 205; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 206; UNSAFE-NEXT: maxsd %xmm0, %xmm1 207; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 208; UNSAFE-NEXT: ret 209; FINITE: x_olt_inverse: 210; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 211; FINITE-NEXT: maxsd %xmm0, %xmm1 212; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 213; FINITE-NEXT: ret 214define double @x_olt_inverse(double %x) nounwind { 215 %c = fcmp olt double %x, 0.000000e+00 216 %d = select i1 %c, double 0.000000e+00, double %x 217 ret double %d 218} 219 220; CHECK: x_oge: 221; CHECK: ucomisd %xmm1, %xmm0 222; UNSAFE: x_oge: 223; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 224; UNSAFE-NEXT: maxsd %xmm1, %xmm0 225; UNSAFE-NEXT: ret 226; FINITE: x_oge: 227; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 228; FINITE-NEXT: maxsd %xmm1, %xmm0 229; FINITE-NEXT: ret 230define double @x_oge(double %x) nounwind { 231 %c = fcmp oge double %x, 0.000000e+00 232 %d = select i1 %c, double %x, double 0.000000e+00 233 ret double %d 234} 235 236; CHECK: x_ole: 237; CHECK: ucomisd %xmm0, %xmm1 238; UNSAFE: x_ole: 239; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 240; UNSAFE-NEXT: minsd %xmm1, %xmm0 241; UNSAFE-NEXT: ret 242; FINITE: x_ole: 243; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 244; FINITE-NEXT: minsd %xmm1, %xmm0 245; FINITE-NEXT: ret 246define double @x_ole(double %x) nounwind { 247 %c = fcmp ole double %x, 0.000000e+00 248 %d = select i1 %c, double %x, double 0.000000e+00 249 ret double %d 250} 251 252; CHECK: x_oge_inverse: 253; CHECK: ucomisd %xmm1, %xmm0 254; UNSAFE: x_oge_inverse: 255; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 256; UNSAFE-NEXT: minsd %xmm0, %xmm1 257; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 258; UNSAFE-NEXT: ret 259; FINITE: x_oge_inverse: 260; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 261; FINITE-NEXT: minsd %xmm0, %xmm1 262; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 263; FINITE-NEXT: ret 264define double @x_oge_inverse(double %x) nounwind { 265 %c = fcmp oge double %x, 0.000000e+00 266 %d = select i1 %c, double 0.000000e+00, double %x 267 ret double %d 268} 269 270; CHECK: x_ole_inverse: 271; CHECK: ucomisd %xmm0, %xmm1 272; UNSAFE: x_ole_inverse: 273; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 274; UNSAFE-NEXT: maxsd %xmm0, %xmm1 275; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 276; UNSAFE-NEXT: ret 277; FINITE: x_ole_inverse: 278; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 279; FINITE-NEXT: maxsd %xmm0, %xmm1 280; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 281; FINITE-NEXT: ret 282define double @x_ole_inverse(double %x) nounwind { 283 %c = fcmp ole double %x, 0.000000e+00 284 %d = select i1 %c, double 0.000000e+00, double %x 285 ret double %d 286} 287 288; CHECK: ugt: 289; CHECK: ucomisd %xmm0, %xmm1 290; UNSAFE: ugt: 291; UNSAFE-NEXT: maxsd %xmm1, %xmm0 292; UNSAFE-NEXT: ret 293; FINITE: ugt: 294; FINITE-NEXT: maxsd %xmm1, %xmm0 295; FINITE-NEXT: ret 296define double @ugt(double %x, double %y) nounwind { 297 %c = fcmp ugt double %x, %y 298 %d = select i1 %c, double %x, double %y 299 ret double %d 300} 301 302; CHECK: ult: 303; CHECK: ucomisd %xmm1, %xmm0 304; UNSAFE: ult: 305; UNSAFE-NEXT: minsd %xmm1, %xmm0 306; UNSAFE-NEXT: ret 307; FINITE: ult: 308; FINITE-NEXT: minsd %xmm1, %xmm0 309; FINITE-NEXT: ret 310define double @ult(double %x, double %y) nounwind { 311 %c = fcmp ult double %x, %y 312 %d = select i1 %c, double %x, double %y 313 ret double %d 314} 315 316; CHECK: ugt_inverse: 317; CHECK: ucomisd %xmm0, %xmm1 318; UNSAFE: ugt_inverse: 319; UNSAFE-NEXT: minsd %xmm0, %xmm1 320; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 321; UNSAFE-NEXT: ret 322; FINITE: ugt_inverse: 323; FINITE-NEXT: minsd %xmm0, %xmm1 324; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 325; FINITE-NEXT: ret 326define double @ugt_inverse(double %x, double %y) nounwind { 327 %c = fcmp ugt double %x, %y 328 %d = select i1 %c, double %y, double %x 329 ret double %d 330} 331 332; CHECK: ult_inverse: 333; CHECK: ucomisd %xmm1, %xmm0 334; UNSAFE: ult_inverse: 335; UNSAFE-NEXT: maxsd %xmm0, %xmm1 336; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 337; UNSAFE-NEXT: ret 338; FINITE: ult_inverse: 339; FINITE-NEXT: maxsd %xmm0, %xmm1 340; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 341; FINITE-NEXT: ret 342define double @ult_inverse(double %x, double %y) nounwind { 343 %c = fcmp ult double %x, %y 344 %d = select i1 %c, double %y, double %x 345 ret double %d 346} 347 348; CHECK: uge: 349; CHECK-NEXT: maxsd %xmm0, %xmm1 350; CHECK-NEXT: movap{{[sd]}} %xmm1, %xmm0 351; CHECK-NEXT: ret 352; UNSAFE: uge: 353; UNSAFE-NEXT: maxsd %xmm1, %xmm0 354; UNSAFE-NEXT: ret 355; FINITE: uge: 356; FINITE-NEXT: maxsd %xmm1, %xmm0 357; FINITE-NEXT: ret 358define double @uge(double %x, double %y) nounwind { 359 %c = fcmp uge double %x, %y 360 %d = select i1 %c, double %x, double %y 361 ret double %d 362} 363 364; CHECK: ule: 365; CHECK-NEXT: minsd %xmm0, %xmm1 366; CHECK-NEXT: movap{{[sd]}} %xmm1, %xmm0 367; CHECK-NEXT: ret 368; UNSAFE: ule: 369; UNSAFE-NEXT: minsd %xmm1, %xmm0 370; UNSAFE-NEXT: ret 371; FINITE: ule: 372; FINITE-NEXT: minsd %xmm1, %xmm0 373; FINITE-NEXT: ret 374define double @ule(double %x, double %y) nounwind { 375 %c = fcmp ule double %x, %y 376 %d = select i1 %c, double %x, double %y 377 ret double %d 378} 379 380; CHECK: uge_inverse: 381; CHECK-NEXT: minsd %xmm1, %xmm0 382; CHECK-NEXT: ret 383; UNSAFE: uge_inverse: 384; UNSAFE-NEXT: minsd %xmm0, %xmm1 385; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 386; UNSAFE-NEXT: ret 387; FINITE: uge_inverse: 388; FINITE-NEXT: minsd %xmm0, %xmm1 389; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 390; FINITE-NEXT: ret 391define double @uge_inverse(double %x, double %y) nounwind { 392 %c = fcmp uge double %x, %y 393 %d = select i1 %c, double %y, double %x 394 ret double %d 395} 396 397; CHECK: ule_inverse: 398; CHECK-NEXT: maxsd %xmm1, %xmm0 399; CHECK-NEXT: ret 400; UNSAFE: ule_inverse: 401; UNSAFE-NEXT: maxsd %xmm0, %xmm1 402; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 403; UNSAFE-NEXT: ret 404; FINITE: ule_inverse: 405; FINITE-NEXT: maxsd %xmm0, %xmm1 406; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 407; FINITE-NEXT: ret 408define double @ule_inverse(double %x, double %y) nounwind { 409 %c = fcmp ule double %x, %y 410 %d = select i1 %c, double %y, double %x 411 ret double %d 412} 413 414; CHECK: x_ugt: 415; CHECK: ucomisd %xmm0, %xmm1 416; UNSAFE: x_ugt: 417; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 418; UNSAFE-NEXT: maxsd %xmm1, %xmm0 419; UNSAFE-NEXT: ret 420; FINITE: x_ugt: 421; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 422; FINITE-NEXT: maxsd %xmm1, %xmm0 423; FINITE-NEXT: ret 424define double @x_ugt(double %x) nounwind { 425 %c = fcmp ugt double %x, 0.000000e+00 426 %d = select i1 %c, double %x, double 0.000000e+00 427 ret double %d 428} 429 430; CHECK: x_ult: 431; CHECK: ucomisd %xmm1, %xmm0 432; UNSAFE: x_ult: 433; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 434; UNSAFE-NEXT: minsd %xmm1, %xmm0 435; UNSAFE-NEXT: ret 436; FINITE: x_ult: 437; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 438; FINITE-NEXT: minsd %xmm1, %xmm0 439; FINITE-NEXT: ret 440define double @x_ult(double %x) nounwind { 441 %c = fcmp ult double %x, 0.000000e+00 442 %d = select i1 %c, double %x, double 0.000000e+00 443 ret double %d 444} 445 446; CHECK: x_ugt_inverse: 447; CHECK: ucomisd %xmm0, %xmm1 448; UNSAFE: x_ugt_inverse: 449; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 450; UNSAFE-NEXT: minsd %xmm0, %xmm1 451; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 452; UNSAFE-NEXT: ret 453; FINITE: x_ugt_inverse: 454; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 455; FINITE-NEXT: minsd %xmm0, %xmm1 456; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 457; FINITE-NEXT: ret 458define double @x_ugt_inverse(double %x) nounwind { 459 %c = fcmp ugt double %x, 0.000000e+00 460 %d = select i1 %c, double 0.000000e+00, double %x 461 ret double %d 462} 463 464; CHECK: x_ult_inverse: 465; CHECK: ucomisd %xmm1, %xmm0 466; UNSAFE: x_ult_inverse: 467; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 468; UNSAFE-NEXT: maxsd %xmm0, %xmm1 469; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 470; UNSAFE-NEXT: ret 471; FINITE: x_ult_inverse: 472; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 473; FINITE-NEXT: maxsd %xmm0, %xmm1 474; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 475; FINITE-NEXT: ret 476define double @x_ult_inverse(double %x) nounwind { 477 %c = fcmp ult double %x, 0.000000e+00 478 %d = select i1 %c, double 0.000000e+00, double %x 479 ret double %d 480} 481 482; CHECK: x_uge: 483; CHECK-NEXT: xorp{{[sd]}} %xmm1, %xmm1 484; CHECK-NEXT: maxsd %xmm0, %xmm1 485; CHECK-NEXT: movap{{[sd]}} %xmm1, %xmm0 486; CHECK-NEXT: ret 487; UNSAFE: x_uge: 488; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 489; UNSAFE-NEXT: maxsd %xmm1, %xmm0 490; UNSAFE-NEXT: ret 491; FINITE: x_uge: 492; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 493; FINITE-NEXT: maxsd %xmm1, %xmm0 494; FINITE-NEXT: ret 495define double @x_uge(double %x) nounwind { 496 %c = fcmp uge double %x, 0.000000e+00 497 %d = select i1 %c, double %x, double 0.000000e+00 498 ret double %d 499} 500 501; CHECK: x_ule: 502; CHECK-NEXT: xorp{{[sd]}} %xmm1, %xmm1 503; CHECK-NEXT: minsd %xmm0, %xmm1 504; CHECK-NEXT: movap{{[sd]}} %xmm1, %xmm0 505; CHECK-NEXT: ret 506; UNSAFE: x_ule: 507; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 508; UNSAFE-NEXT: minsd %xmm1, %xmm0 509; UNSAFE-NEXT: ret 510; FINITE: x_ule: 511; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 512; FINITE-NEXT: minsd %xmm1, %xmm0 513; FINITE-NEXT: ret 514define double @x_ule(double %x) nounwind { 515 %c = fcmp ule double %x, 0.000000e+00 516 %d = select i1 %c, double %x, double 0.000000e+00 517 ret double %d 518} 519 520; CHECK: x_uge_inverse: 521; CHECK-NEXT: xorp{{[sd]}} %xmm1, %xmm1 522; CHECK-NEXT: minsd %xmm1, %xmm0 523; CHECK-NEXT: ret 524; UNSAFE: x_uge_inverse: 525; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 526; UNSAFE-NEXT: minsd %xmm0, %xmm1 527; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 528; UNSAFE-NEXT: ret 529; FINITE: x_uge_inverse: 530; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 531; FINITE-NEXT: minsd %xmm0, %xmm1 532; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 533; FINITE-NEXT: ret 534define double @x_uge_inverse(double %x) nounwind { 535 %c = fcmp uge double %x, 0.000000e+00 536 %d = select i1 %c, double 0.000000e+00, double %x 537 ret double %d 538} 539 540; CHECK: x_ule_inverse: 541; CHECK-NEXT: xorp{{[sd]}} %xmm1, %xmm1 542; CHECK-NEXT: maxsd %xmm1, %xmm0 543; CHECK-NEXT: ret 544; UNSAFE: x_ule_inverse: 545; UNSAFE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 546; UNSAFE-NEXT: maxsd %xmm0, %xmm1 547; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 548; UNSAFE-NEXT: ret 549; FINITE: x_ule_inverse: 550; FINITE-NEXT: xorp{{[sd]}} %xmm1, %xmm1 551; FINITE-NEXT: maxsd %xmm0, %xmm1 552; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 553; FINITE-NEXT: ret 554define double @x_ule_inverse(double %x) nounwind { 555 %c = fcmp ule double %x, 0.000000e+00 556 %d = select i1 %c, double 0.000000e+00, double %x 557 ret double %d 558} 559 560; CHECK: y_ogt: 561; CHECK-NEXT: maxsd {{[^,]*}}, %xmm0 562; CHECK-NEXT: ret 563; UNSAFE: y_ogt: 564; UNSAFE-NEXT: maxsd {{[^,]*}}, %xmm0 565; UNSAFE-NEXT: ret 566; FINITE: y_ogt: 567; FINITE-NEXT: maxsd {{[^,]*}}, %xmm0 568; FINITE-NEXT: ret 569define double @y_ogt(double %x) nounwind { 570 %c = fcmp ogt double %x, -0.000000e+00 571 %d = select i1 %c, double %x, double -0.000000e+00 572 ret double %d 573} 574 575; CHECK: y_olt: 576; CHECK-NEXT: minsd {{[^,]*}}, %xmm0 577; CHECK-NEXT: ret 578; UNSAFE: y_olt: 579; UNSAFE-NEXT: minsd {{[^,]*}}, %xmm0 580; UNSAFE-NEXT: ret 581; FINITE: y_olt: 582; FINITE-NEXT: minsd {{[^,]*}}, %xmm0 583; FINITE-NEXT: ret 584define double @y_olt(double %x) nounwind { 585 %c = fcmp olt double %x, -0.000000e+00 586 %d = select i1 %c, double %x, double -0.000000e+00 587 ret double %d 588} 589 590; CHECK: y_ogt_inverse: 591; CHECK-NEXT: movsd {{[^,]*}}, %xmm1 592; CHECK-NEXT: minsd %xmm0, %xmm1 593; CHECK-NEXT: movap{{[sd]}} %xmm1, %xmm0 594; CHECK-NEXT: ret 595; UNSAFE: y_ogt_inverse: 596; UNSAFE-NEXT: movsd {{[^,]*}}, %xmm1 597; UNSAFE-NEXT: minsd %xmm0, %xmm1 598; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 599; UNSAFE-NEXT: ret 600; FINITE: y_ogt_inverse: 601; FINITE-NEXT: movsd {{[^,]*}}, %xmm1 602; FINITE-NEXT: minsd %xmm0, %xmm1 603; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 604; FINITE-NEXT: ret 605define double @y_ogt_inverse(double %x) nounwind { 606 %c = fcmp ogt double %x, -0.000000e+00 607 %d = select i1 %c, double -0.000000e+00, double %x 608 ret double %d 609} 610 611; CHECK: y_olt_inverse: 612; CHECK-NEXT: movsd {{[^,]*}}, %xmm1 613; CHECK-NEXT: maxsd %xmm0, %xmm1 614; CHECK-NEXT: movap{{[sd]}} %xmm1, %xmm0 615; CHECK-NEXT: ret 616; UNSAFE: y_olt_inverse: 617; UNSAFE-NEXT: movsd {{[^,]*}}, %xmm1 618; UNSAFE-NEXT: maxsd %xmm0, %xmm1 619; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 620; UNSAFE-NEXT: ret 621; FINITE: y_olt_inverse: 622; FINITE-NEXT: movsd {{[^,]*}}, %xmm1 623; FINITE-NEXT: maxsd %xmm0, %xmm1 624; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 625; FINITE-NEXT: ret 626define double @y_olt_inverse(double %x) nounwind { 627 %c = fcmp olt double %x, -0.000000e+00 628 %d = select i1 %c, double -0.000000e+00, double %x 629 ret double %d 630} 631 632; CHECK: y_oge: 633; CHECK: ucomisd %xmm1, %xmm0 634; UNSAFE: y_oge: 635; UNSAFE-NEXT: maxsd {{[^,]*}}, %xmm0 636; UNSAFE-NEXT: ret 637; FINITE: y_oge: 638; FINITE-NEXT: maxsd {{[^,]*}}, %xmm0 639; FINITE-NEXT: ret 640define double @y_oge(double %x) nounwind { 641 %c = fcmp oge double %x, -0.000000e+00 642 %d = select i1 %c, double %x, double -0.000000e+00 643 ret double %d 644} 645 646; CHECK: y_ole: 647; CHECK: ucomisd %xmm0, %xmm1 648; UNSAFE: y_ole: 649; UNSAFE-NEXT: minsd {{[^,]*}}, %xmm0 650; UNSAFE-NEXT: ret 651; FINITE: y_ole: 652; FINITE-NEXT: minsd {{[^,]*}}, %xmm0 653; FINITE-NEXT: ret 654define double @y_ole(double %x) nounwind { 655 %c = fcmp ole double %x, -0.000000e+00 656 %d = select i1 %c, double %x, double -0.000000e+00 657 ret double %d 658} 659 660; CHECK: y_oge_inverse: 661; CHECK: ucomisd %xmm1, %xmm0 662; UNSAFE: y_oge_inverse: 663; UNSAFE-NEXT: movsd {{[^,]*}}, %xmm1 664; UNSAFE-NEXT: minsd %xmm0, %xmm1 665; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 666; UNSAFE-NEXT: ret 667; FINITE: y_oge_inverse: 668; FINITE-NEXT: movsd {{[^,]*}}, %xmm1 669; FINITE-NEXT: minsd %xmm0, %xmm1 670; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 671; FINITE-NEXT: ret 672define double @y_oge_inverse(double %x) nounwind { 673 %c = fcmp oge double %x, -0.000000e+00 674 %d = select i1 %c, double -0.000000e+00, double %x 675 ret double %d 676} 677 678; CHECK: y_ole_inverse: 679; CHECK: ucomisd %xmm0, %xmm1 680; UNSAFE: y_ole_inverse: 681; UNSAFE-NEXT: movsd {{[^,]*}}, %xmm1 682; UNSAFE-NEXT: maxsd %xmm0, %xmm1 683; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 684; UNSAFE-NEXT: ret 685; FINITE: y_ole_inverse: 686; FINITE-NEXT: movsd {{[^,]*}}, %xmm1 687; FINITE-NEXT: maxsd %xmm0, %xmm1 688; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 689; FINITE-NEXT: ret 690define double @y_ole_inverse(double %x) nounwind { 691 %c = fcmp ole double %x, -0.000000e+00 692 %d = select i1 %c, double -0.000000e+00, double %x 693 ret double %d 694} 695 696; CHECK: y_ugt: 697; CHECK: ucomisd %xmm0, %xmm1 698; UNSAFE: y_ugt: 699; UNSAFE-NEXT: maxsd {{[^,]*}}, %xmm0 700; UNSAFE-NEXT: ret 701; FINITE: y_ugt: 702; FINITE-NEXT: maxsd {{[^,]*}}, %xmm0 703; FINITE-NEXT: ret 704define double @y_ugt(double %x) nounwind { 705 %c = fcmp ugt double %x, -0.000000e+00 706 %d = select i1 %c, double %x, double -0.000000e+00 707 ret double %d 708} 709 710; CHECK: y_ult: 711; CHECK: ucomisd %xmm1, %xmm0 712; UNSAFE: y_ult: 713; UNSAFE-NEXT: minsd {{[^,]*}}, %xmm0 714; UNSAFE-NEXT: ret 715; FINITE: y_ult: 716; FINITE-NEXT: minsd {{[^,]*}}, %xmm0 717; FINITE-NEXT: ret 718define double @y_ult(double %x) nounwind { 719 %c = fcmp ult double %x, -0.000000e+00 720 %d = select i1 %c, double %x, double -0.000000e+00 721 ret double %d 722} 723 724; CHECK: y_ugt_inverse: 725; CHECK: ucomisd %xmm0, %xmm1 726; UNSAFE: y_ugt_inverse: 727; UNSAFE-NEXT: movsd {{[^,]*}}, %xmm1 728; UNSAFE-NEXT: minsd %xmm0, %xmm1 729; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 730; UNSAFE-NEXT: ret 731; FINITE: y_ugt_inverse: 732; FINITE-NEXT: movsd {{[^,]*}}, %xmm1 733; FINITE-NEXT: minsd %xmm0, %xmm1 734; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 735; FINITE-NEXT: ret 736define double @y_ugt_inverse(double %x) nounwind { 737 %c = fcmp ugt double %x, -0.000000e+00 738 %d = select i1 %c, double -0.000000e+00, double %x 739 ret double %d 740} 741 742; CHECK: y_ult_inverse: 743; CHECK: ucomisd %xmm1, %xmm0 744; UNSAFE: y_ult_inverse: 745; UNSAFE-NEXT: movsd {{[^,]*}}, %xmm1 746; UNSAFE-NEXT: maxsd %xmm0, %xmm1 747; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 748; UNSAFE-NEXT: ret 749; FINITE: y_ult_inverse: 750; FINITE-NEXT: movsd {{[^,]*}}, %xmm1 751; FINITE-NEXT: maxsd %xmm0, %xmm1 752; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 753; FINITE-NEXT: ret 754define double @y_ult_inverse(double %x) nounwind { 755 %c = fcmp ult double %x, -0.000000e+00 756 %d = select i1 %c, double -0.000000e+00, double %x 757 ret double %d 758} 759 760; CHECK: y_uge: 761; CHECK-NEXT: movsd {{[^,]*}}, %xmm1 762; CHECK-NEXT: maxsd %xmm0, %xmm1 763; CHECK-NEXT: movap{{[sd]}} %xmm1, %xmm0 764; CHECK-NEXT: ret 765; UNSAFE: y_uge: 766; UNSAFE-NEXT: maxsd {{[^,]*}}, %xmm0 767; UNSAFE-NEXT: ret 768; FINITE: y_uge: 769; FINITE-NEXT: maxsd {{[^,]*}}, %xmm0 770; FINITE-NEXT: ret 771define double @y_uge(double %x) nounwind { 772 %c = fcmp uge double %x, -0.000000e+00 773 %d = select i1 %c, double %x, double -0.000000e+00 774 ret double %d 775} 776 777; CHECK: y_ule: 778; CHECK-NEXT: movsd {{[^,]*}}, %xmm1 779; CHECK-NEXT: minsd %xmm0, %xmm1 780; CHECK-NEXT: movap{{[sd]}} %xmm1, %xmm0 781; CHECK-NEXT: ret 782; UNSAFE: y_ule: 783; UNSAFE-NEXT: minsd {{[^,]*}}, %xmm0 784; UNSAFE-NEXT: ret 785; FINITE: y_ule: 786; FINITE-NEXT: minsd {{[^,]*}}, %xmm0 787; FINITE-NEXT: ret 788define double @y_ule(double %x) nounwind { 789 %c = fcmp ule double %x, -0.000000e+00 790 %d = select i1 %c, double %x, double -0.000000e+00 791 ret double %d 792} 793 794; CHECK: y_uge_inverse: 795; CHECK-NEXT: minsd {{[^,]*}}, %xmm0 796; CHECK-NEXT: ret 797; UNSAFE: y_uge_inverse: 798; UNSAFE-NEXT: movsd {{[^,]*}}, %xmm1 799; UNSAFE-NEXT: minsd %xmm0, %xmm1 800; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 801; UNSAFE-NEXT: ret 802; FINITE: y_uge_inverse: 803; FINITE-NEXT: movsd {{[^,]*}}, %xmm1 804; FINITE-NEXT: minsd %xmm0, %xmm1 805; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 806; FINITE-NEXT: ret 807define double @y_uge_inverse(double %x) nounwind { 808 %c = fcmp uge double %x, -0.000000e+00 809 %d = select i1 %c, double -0.000000e+00, double %x 810 ret double %d 811} 812 813; CHECK: y_ule_inverse: 814; CHECK-NEXT: maxsd {{[^,]*}}, %xmm0 815; CHECK-NEXT: ret 816; UNSAFE: y_ule_inverse: 817; UNSAFE-NEXT: movsd {{[^,]*}}, %xmm1 818; UNSAFE-NEXT: maxsd %xmm0, %xmm1 819; UNSAFE-NEXT: movap{{[sd]}} %xmm1, %xmm0 820; UNSAFE-NEXT: ret 821; FINITE: y_ule_inverse: 822; FINITE-NEXT: movsd {{[^,]*}}, %xmm1 823; FINITE-NEXT: maxsd %xmm0, %xmm1 824; FINITE-NEXT: movap{{[sd]}} %xmm1, %xmm0 825; FINITE-NEXT: ret 826define double @y_ule_inverse(double %x) nounwind { 827 %c = fcmp ule double %x, -0.000000e+00 828 %d = select i1 %c, double -0.000000e+00, double %x 829 ret double %d 830} 831; Test a few more misc. cases. 832 833; CHECK: clampTo3k_a: 834; CHECK: minsd 835; UNSAFE: clampTo3k_a: 836; UNSAFE: minsd 837; FINITE: clampTo3k_a: 838; FINITE: minsd 839define double @clampTo3k_a(double %x) nounwind readnone { 840entry: 841 %0 = fcmp ogt double %x, 3.000000e+03 ; <i1> [#uses=1] 842 %x_addr.0 = select i1 %0, double 3.000000e+03, double %x ; <double> [#uses=1] 843 ret double %x_addr.0 844} 845 846; CHECK: clampTo3k_b: 847; CHECK: minsd 848; UNSAFE: clampTo3k_b: 849; UNSAFE: minsd 850; FINITE: clampTo3k_b: 851; FINITE: minsd 852define double @clampTo3k_b(double %x) nounwind readnone { 853entry: 854 %0 = fcmp uge double %x, 3.000000e+03 ; <i1> [#uses=1] 855 %x_addr.0 = select i1 %0, double 3.000000e+03, double %x ; <double> [#uses=1] 856 ret double %x_addr.0 857} 858 859; CHECK: clampTo3k_c: 860; CHECK: maxsd 861; UNSAFE: clampTo3k_c: 862; UNSAFE: maxsd 863; FINITE: clampTo3k_c: 864; FINITE: maxsd 865define double @clampTo3k_c(double %x) nounwind readnone { 866entry: 867 %0 = fcmp olt double %x, 3.000000e+03 ; <i1> [#uses=1] 868 %x_addr.0 = select i1 %0, double 3.000000e+03, double %x ; <double> [#uses=1] 869 ret double %x_addr.0 870} 871 872; CHECK: clampTo3k_d: 873; CHECK: maxsd 874; UNSAFE: clampTo3k_d: 875; UNSAFE: maxsd 876; FINITE: clampTo3k_d: 877; FINITE: maxsd 878define double @clampTo3k_d(double %x) nounwind readnone { 879entry: 880 %0 = fcmp ule double %x, 3.000000e+03 ; <i1> [#uses=1] 881 %x_addr.0 = select i1 %0, double 3.000000e+03, double %x ; <double> [#uses=1] 882 ret double %x_addr.0 883} 884 885; CHECK: clampTo3k_e: 886; CHECK: maxsd 887; UNSAFE: clampTo3k_e: 888; UNSAFE: maxsd 889; FINITE: clampTo3k_e: 890; FINITE: maxsd 891define double @clampTo3k_e(double %x) nounwind readnone { 892entry: 893 %0 = fcmp olt double %x, 3.000000e+03 ; <i1> [#uses=1] 894 %x_addr.0 = select i1 %0, double 3.000000e+03, double %x ; <double> [#uses=1] 895 ret double %x_addr.0 896} 897 898; CHECK: clampTo3k_f: 899; CHECK: maxsd 900; UNSAFE: clampTo3k_f: 901; UNSAFE: maxsd 902; FINITE: clampTo3k_f: 903; FINITE: maxsd 904define double @clampTo3k_f(double %x) nounwind readnone { 905entry: 906 %0 = fcmp ule double %x, 3.000000e+03 ; <i1> [#uses=1] 907 %x_addr.0 = select i1 %0, double 3.000000e+03, double %x ; <double> [#uses=1] 908 ret double %x_addr.0 909} 910 911; CHECK: clampTo3k_g: 912; CHECK: minsd 913; UNSAFE: clampTo3k_g: 914; UNSAFE: minsd 915; FINITE: clampTo3k_g: 916; FINITE: minsd 917define double @clampTo3k_g(double %x) nounwind readnone { 918entry: 919 %0 = fcmp ogt double %x, 3.000000e+03 ; <i1> [#uses=1] 920 %x_addr.0 = select i1 %0, double 3.000000e+03, double %x ; <double> [#uses=1] 921 ret double %x_addr.0 922} 923 924; CHECK: clampTo3k_h: 925; CHECK: minsd 926; UNSAFE: clampTo3k_h: 927; UNSAFE: minsd 928; FINITE: clampTo3k_h: 929; FINITE: minsd 930define double @clampTo3k_h(double %x) nounwind readnone { 931entry: 932 %0 = fcmp uge double %x, 3.000000e+03 ; <i1> [#uses=1] 933 %x_addr.0 = select i1 %0, double 3.000000e+03, double %x ; <double> [#uses=1] 934 ret double %x_addr.0 935} 936 937; UNSAFE: maxpd: 938; UNSAFE: maxpd 939define <2 x double> @maxpd(<2 x double> %x, <2 x double> %y) { 940 %max_is_x = fcmp oge <2 x double> %x, %y 941 %max = select <2 x i1> %max_is_x, <2 x double> %x, <2 x double> %y 942 ret <2 x double> %max 943} 944 945; UNSAFE: minpd: 946; UNSAFE: minpd 947define <2 x double> @minpd(<2 x double> %x, <2 x double> %y) { 948 %min_is_x = fcmp ole <2 x double> %x, %y 949 %min = select <2 x i1> %min_is_x, <2 x double> %x, <2 x double> %y 950 ret <2 x double> %min 951} 952 953; UNSAFE: maxps: 954; UNSAFE: maxps 955define <4 x float> @maxps(<4 x float> %x, <4 x float> %y) { 956 %max_is_x = fcmp oge <4 x float> %x, %y 957 %max = select <4 x i1> %max_is_x, <4 x float> %x, <4 x float> %y 958 ret <4 x float> %max 959} 960 961; UNSAFE: minps: 962; UNSAFE: minps 963define <4 x float> @minps(<4 x float> %x, <4 x float> %y) { 964 %min_is_x = fcmp ole <4 x float> %x, %y 965 %min = select <4 x i1> %min_is_x, <4 x float> %x, <4 x float> %y 966 ret <4 x float> %min 967} 968