@@ -483,5 +483,174 @@ if.else:
483
483
ret i64 13
484
484
}
485
485
486
+ define i1 @test_sign_pos (float %x ) {
487
+ ; CHECK-LABEL: @test_sign_pos(
488
+ ; CHECK-NEXT: [[FABS:%.*]] = call float @llvm.fabs.f32(float [[X:%.*]])
489
+ ; CHECK-NEXT: [[Y:%.*]] = bitcast float [[FABS]] to i32
490
+ ; CHECK-NEXT: [[SIGN:%.*]] = icmp sgt i32 [[Y]], -1
491
+ ; CHECK-NEXT: ret i1 [[SIGN]]
492
+ ;
493
+ %fabs = call float @llvm.fabs.f32 (float %x )
494
+ %y = bitcast float %fabs to i32
495
+ %sign = icmp sgt i32 %y , -1
496
+ ret i1 %sign
497
+ }
498
+
499
+ define i1 @test_sign_neg (float %x ) {
500
+ ; CHECK-LABEL: @test_sign_neg(
501
+ ; CHECK-NEXT: [[FABS:%.*]] = call float @llvm.fabs.f32(float [[X:%.*]])
502
+ ; CHECK-NEXT: [[FNABS:%.*]] = fneg float [[FABS]]
503
+ ; CHECK-NEXT: [[Y:%.*]] = bitcast float [[FNABS]] to i32
504
+ ; CHECK-NEXT: [[SIGN:%.*]] = icmp slt i32 [[Y]], 0
505
+ ; CHECK-NEXT: ret i1 [[SIGN]]
506
+ ;
507
+ %fabs = call float @llvm.fabs.f32 (float %x )
508
+ %fnabs = fneg float %fabs
509
+ %y = bitcast float %fnabs to i32
510
+ %sign = icmp slt i32 %y , 0
511
+ ret i1 %sign
512
+ }
513
+
514
+ define <2 x i1 > @test_sign_pos_vec (<2 x float > %x ) {
515
+ ; CHECK-LABEL: @test_sign_pos_vec(
516
+ ; CHECK-NEXT: [[FABS:%.*]] = call <2 x float> @llvm.fabs.v2f32(<2 x float> [[X:%.*]])
517
+ ; CHECK-NEXT: [[Y:%.*]] = bitcast <2 x float> [[FABS]] to <2 x i32>
518
+ ; CHECK-NEXT: [[SIGN:%.*]] = icmp slt <2 x i32> [[Y]], zeroinitializer
519
+ ; CHECK-NEXT: ret <2 x i1> [[SIGN]]
520
+ ;
521
+ %fabs = call <2 x float > @llvm.fabs.v2f32 (<2 x float > %x )
522
+ %y = bitcast <2 x float > %fabs to <2 x i32 >
523
+ %sign = icmp slt <2 x i32 > %y , zeroinitializer
524
+ ret <2 x i1 > %sign
525
+ }
526
+
527
+ define i32 @test_inf_only (float nofpclass(nan sub norm zero) %x ) {
528
+ ; CHECK-LABEL: @test_inf_only(
529
+ ; CHECK-NEXT: [[TMP1:%.*]] = call float @llvm.fabs.f32(float [[X:%.*]])
530
+ ; CHECK-NEXT: [[AND:%.*]] = bitcast float [[TMP1]] to i32
531
+ ; CHECK-NEXT: ret i32 [[AND]]
532
+ ;
533
+ %y = bitcast float %x to i32
534
+ %and = and i32 %y , 2147483647
535
+ ret i32 %and
536
+ }
537
+
538
+ define i32 @test_zero_only (float nofpclass(nan sub norm inf) %x ) {
539
+ ; CHECK-LABEL: @test_zero_only(
540
+ ; CHECK-NEXT: [[TMP1:%.*]] = call float @llvm.fabs.f32(float [[X:%.*]])
541
+ ; CHECK-NEXT: [[AND:%.*]] = bitcast float [[TMP1]] to i32
542
+ ; CHECK-NEXT: ret i32 [[AND]]
543
+ ;
544
+ %y = bitcast float %x to i32
545
+ %and = and i32 %y , 2147483647
546
+ ret i32 %and
547
+ }
548
+
549
+ define i32 @test_inf_nan_only (float nofpclass(sub norm zero) %x ) {
550
+ ; CHECK-LABEL: @test_inf_nan_only(
551
+ ; CHECK-NEXT: [[Y:%.*]] = bitcast float [[X:%.*]] to i32
552
+ ; CHECK-NEXT: [[AND:%.*]] = and i32 [[Y]], 2130706432
553
+ ; CHECK-NEXT: ret i32 [[AND]]
554
+ ;
555
+ %y = bitcast float %x to i32
556
+ %and = and i32 %y , 2130706432
557
+ ret i32 %and
558
+ }
559
+
560
+ define i32 @test_sub_zero_only (float nofpclass(nan norm inf) %x ) {
561
+ ; CHECK-LABEL: @test_sub_zero_only(
562
+ ; CHECK-NEXT: [[Y:%.*]] = bitcast float [[X:%.*]] to i32
563
+ ; CHECK-NEXT: [[AND:%.*]] = and i32 [[Y]], 2130706432
564
+ ; CHECK-NEXT: ret i32 [[AND]]
565
+ ;
566
+ %y = bitcast float %x to i32
567
+ %and = and i32 %y , 2130706432
568
+ ret i32 %and
569
+ }
570
+
571
+ define i32 @test_inf_zero_only (float nofpclass(nan norm sub ) %x ) {
572
+ ; CHECK-LABEL: @test_inf_zero_only(
573
+ ; CHECK-NEXT: [[Y:%.*]] = bitcast float [[X:%.*]] to i32
574
+ ; CHECK-NEXT: [[AND:%.*]] = and i32 [[Y]], 16777215
575
+ ; CHECK-NEXT: ret i32 [[AND]]
576
+ ;
577
+ %y = bitcast float %x to i32
578
+ %and = and i32 %y , 16777215
579
+ ret i32 %and
580
+ }
581
+
582
+ define i1 @test_simplify_icmp (i32 %x ) {
583
+ ; CHECK-LABEL: @test_simplify_icmp(
584
+ ; CHECK-NEXT: [[CONV_I_I:%.*]] = uitofp i32 [[X:%.*]] to double
585
+ ; CHECK-NEXT: [[TMP1:%.*]] = bitcast double [[CONV_I_I]] to i64
586
+ ; CHECK-NEXT: [[SHR_I_MASK_I:%.*]] = and i64 [[TMP1]], -140737488355328
587
+ ; CHECK-NEXT: [[CMP_I:%.*]] = icmp eq i64 [[SHR_I_MASK_I]], -1970324836974592
588
+ ; CHECK-NEXT: ret i1 [[CMP_I]]
589
+ ;
590
+ %conv.i.i = uitofp i32 %x to double
591
+ %3 = bitcast double %conv.i.i to i64
592
+ %shr.i.mask.i = and i64 %3 , -140737488355328
593
+ %cmp.i = icmp eq i64 %shr.i.mask.i , -1970324836974592
594
+ ret i1 %cmp.i
595
+ }
596
+
597
+ define i16 @test_simplify_mask (i32 %ui , float %x ) {
598
+ ; CHECK-LABEL: @test_simplify_mask(
599
+ ; CHECK-NEXT: [[CONV:%.*]] = uitofp i32 [[UI:%.*]] to float
600
+ ; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt float [[CONV]], [[X:%.*]]
601
+ ; CHECK-NEXT: br i1 [[CMP]], label [[IF_ELSE:%.*]], label [[IF_END:%.*]]
602
+ ; CHECK: if.end:
603
+ ; CHECK-NEXT: [[CAST:%.*]] = bitcast float [[CONV]] to i32
604
+ ; CHECK-NEXT: [[SHR:%.*]] = lshr i32 [[CAST]], 16
605
+ ; CHECK-NEXT: [[TRUNC:%.*]] = trunc i32 [[SHR]] to i16
606
+ ; CHECK-NEXT: [[AND:%.*]] = and i16 [[TRUNC]], -32768
607
+ ; CHECK-NEXT: [[OR:%.*]] = or disjoint i16 [[AND]], 31744
608
+ ; CHECK-NEXT: ret i16 [[OR]]
609
+ ; CHECK: if.else:
610
+ ; CHECK-NEXT: ret i16 0
611
+ ;
612
+ %conv = uitofp i32 %ui to float
613
+ %cmp = fcmp olt float %x , %conv
614
+ br i1 %cmp , label %if.else , label %if.end
615
+
616
+ if.end:
617
+ %cast = bitcast float %conv to i32
618
+ %shr = lshr i32 %cast , 16
619
+ %trunc = trunc i32 %shr to i16
620
+ %and = and i16 %trunc , -32768
621
+ %or = or disjoint i16 %and , 31744
622
+ ret i16 %or
623
+
624
+ if.else:
625
+ ret i16 0
626
+ }
627
+
628
+ ; TODO: %cmp always evaluates to false
629
+
630
+ define i1 @test_simplify_icmp2 (double %x ) {
631
+ ; CHECK-LABEL: @test_simplify_icmp2(
632
+ ; CHECK-NEXT: [[ABS:%.*]] = tail call double @llvm.fabs.f64(double [[X:%.*]])
633
+ ; CHECK-NEXT: [[COND:%.*]] = fcmp oeq double [[ABS]], 0x7FF0000000000000
634
+ ; CHECK-NEXT: br i1 [[COND]], label [[IF_THEN:%.*]], label [[IF_ELSE:%.*]]
635
+ ; CHECK: if.then:
636
+ ; CHECK-NEXT: [[CAST:%.*]] = bitcast double [[X]] to i64
637
+ ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i64 [[CAST]], 3458764513820540928
638
+ ; CHECK-NEXT: ret i1 [[CMP]]
639
+ ; CHECK: if.else:
640
+ ; CHECK-NEXT: ret i1 false
641
+ ;
642
+ %abs = tail call double @llvm.fabs.f64 (double %x )
643
+ %cond = fcmp oeq double %abs , 0x7FF0000000000000
644
+ br i1 %cond , label %if.then , label %if.else
645
+
646
+ if.then:
647
+ %cast = bitcast double %x to i64
648
+ %cmp = icmp eq i64 %cast , 3458764513820540928
649
+ ret i1 %cmp
650
+
651
+ if.else:
652
+ ret i1 false
653
+ }
654
+
486
655
declare void @use (i1 )
487
656
declare void @sink (i8 )
0 commit comments