@@ -14,7 +14,7 @@ define dso_local void @redundant_stores_merging() {
14
14
; CHECK-LABEL: redundant_stores_merging:
15
15
; CHECK: # %bb.0:
16
16
; CHECK-NEXT: movabsq $1958505086977, %rax # imm = 0x1C800000001
17
- ; CHECK-NEXT: movq %rax, e+{{.*}} (%rip)
17
+ ; CHECK-NEXT: movq %rax, e+4 (%rip)
18
18
; CHECK-NEXT: retq
19
19
store i32 1 , i32* getelementptr inbounds (%structTy , %structTy* @e , i64 0 , i32 1 ), align 4
20
20
store i32 123 , i32* getelementptr inbounds (%structTy , %structTy* @e , i64 0 , i32 2 ), align 4
@@ -27,8 +27,8 @@ define dso_local void @redundant_stores_merging_reverse() {
27
27
; CHECK-LABEL: redundant_stores_merging_reverse:
28
28
; CHECK: # %bb.0:
29
29
; CHECK-NEXT: movabsq $528280977409, %rax # imm = 0x7B00000001
30
- ; CHECK-NEXT: movq %rax, e+{{.*}} (%rip)
31
- ; CHECK-NEXT: movl $456, e+{{.*}} (%rip) # imm = 0x1C8
30
+ ; CHECK-NEXT: movq %rax, e+4 (%rip)
31
+ ; CHECK-NEXT: movl $456, e+8 (%rip) # imm = 0x1C8
32
32
; CHECK-NEXT: retq
33
33
store i32 123 , i32* getelementptr inbounds (%structTy , %structTy* @e , i64 0 , i32 2 ), align 4
34
34
store i32 456 , i32* getelementptr inbounds (%structTy , %structTy* @e , i64 0 , i32 2 ), align 4
@@ -46,8 +46,8 @@ define dso_local void @redundant_stores_merging_reverse() {
46
46
define dso_local void @overlapping_stores_merging () {
47
47
; CHECK-LABEL: overlapping_stores_merging:
48
48
; CHECK: # %bb.0:
49
- ; CHECK-NEXT: movl $1, {{.*}} (%rip)
50
- ; CHECK-NEXT: movw $2, b+{{.*}} (%rip)
49
+ ; CHECK-NEXT: movl $1, b (%rip)
50
+ ; CHECK-NEXT: movw $2, b+3 (%rip)
51
51
; CHECK-NEXT: retq
52
52
store i16 0 , i16* bitcast (i8* getelementptr inbounds ([8 x i8 ], [8 x i8 ]* @b , i64 0 , i64 2 ) to i16* ), align 2
53
53
store i16 2 , i16* bitcast (i8* getelementptr inbounds ([8 x i8 ], [8 x i8 ]* @b , i64 0 , i64 3 ) to i16* ), align 1
@@ -612,3 +612,88 @@ define dso_local void @be_i64_to_i32_order(i64 %x, i32* %p0) {
612
612
store i32 %t0 , i32* %p1 , align 4
613
613
ret void
614
614
}
615
+
616
+ ; https://llvm.org/PR50623
617
+ ; FIXME:
618
+ ; It is a miscompile to merge the stores if we are not
619
+ ; writing all of the bytes from the source value.
620
+
621
+ define void @merge_hole (i32 %x , i8* %p ) {
622
+ ; CHECK-LABEL: merge_hole:
623
+ ; CHECK: # %bb.0:
624
+ ; CHECK-NEXT: movl %edi, (%rsi)
625
+ ; CHECK-NEXT: retq
626
+ %pcast = bitcast i8* %p to i16*
627
+ %p2 = getelementptr inbounds i16 , i16* %pcast , i64 1
628
+ %x3 = trunc i32 %x to i8
629
+ store i8 %x3 , i8* %p , align 1
630
+ %sh = lshr i32 %x , 16
631
+ %x01 = trunc i32 %sh to i16
632
+ store i16 %x01 , i16* %p2 , align 1
633
+ ret void
634
+ }
635
+
636
+ ; Change the order of the stores.
637
+ ; It is a miscompile to merge the stores if we are not
638
+ ; writing all of the bytes from the source value.
639
+
640
+ define void @merge_hole2 (i32 %x , i8* %p ) {
641
+ ; CHECK-LABEL: merge_hole2:
642
+ ; CHECK: # %bb.0:
643
+ ; CHECK-NEXT: movl %edi, %eax
644
+ ; CHECK-NEXT: shrl $16, %eax
645
+ ; CHECK-NEXT: movw %ax, 2(%rsi)
646
+ ; CHECK-NEXT: movb %dil, (%rsi)
647
+ ; CHECK-NEXT: retq
648
+ %pcast = bitcast i8* %p to i16*
649
+ %p2 = getelementptr inbounds i16 , i16* %pcast , i64 1
650
+ %sh = lshr i32 %x , 16
651
+ %x01 = trunc i32 %sh to i16
652
+ store i16 %x01 , i16* %p2 , align 1
653
+ %x3 = trunc i32 %x to i8
654
+ store i8 %x3 , i8* %p , align 1
655
+ ret void
656
+ }
657
+
658
+ ; Change offset.
659
+ ; It is a miscompile to merge the stores if we are not
660
+ ; writing all of the bytes from the source value.
661
+
662
+ define void @merge_hole3 (i32 %x , i8* %p ) {
663
+ ; CHECK-LABEL: merge_hole3:
664
+ ; CHECK: # %bb.0:
665
+ ; CHECK-NEXT: movb %dil, 1(%rsi)
666
+ ; CHECK-NEXT: shrl $16, %edi
667
+ ; CHECK-NEXT: movw %di, 2(%rsi)
668
+ ; CHECK-NEXT: retq
669
+ %p1 = getelementptr inbounds i8 , i8* %p , i64 1
670
+ %pcast = bitcast i8* %p to i16*
671
+ %p2 = getelementptr inbounds i16 , i16* %pcast , i64 1
672
+ %x3 = trunc i32 %x to i8
673
+ store i8 %x3 , i8* %p1 , align 1
674
+ %sh = lshr i32 %x , 16
675
+ %x01 = trunc i32 %sh to i16
676
+ store i16 %x01 , i16* %p2 , align 1
677
+ ret void
678
+ }
679
+
680
+ ; Change offset.
681
+ ; FIXME:
682
+ ; It is a miscompile to merge the stores if we are not
683
+ ; writing all of the bytes from the source value.
684
+
685
+ define void @merge_hole4 (i32 %x , i8* %p ) {
686
+ ; CHECK-LABEL: merge_hole4:
687
+ ; CHECK: # %bb.0:
688
+ ; CHECK-NEXT: rorl $16, %edi
689
+ ; CHECK-NEXT: movl %edi, (%rsi)
690
+ ; CHECK-NEXT: retq
691
+ %pcast = bitcast i8* %p to i16*
692
+ %p2 = getelementptr inbounds i8 , i8* %p , i64 2
693
+ %x3 = trunc i32 %x to i8
694
+ store i8 %x3 , i8* %p2 , align 1
695
+ %sh = lshr i32 %x , 16
696
+ %x01 = trunc i32 %sh to i16
697
+ store i16 %x01 , i16* %pcast , align 1
698
+ ret void
699
+ }
0 commit comments