<table border="1" cellspacing="0" cellpadding="8">
<tr>
<th>Issue</th>
<td>
<a href=https://github.com/llvm/llvm-project/issues/57725>57725</a>
</td>
</tr>
<tr>
<th>Summary</th>
<td>
[stack-coloring] incorrect stack slot merging
</td>
</tr>
<tr>
<th>Labels</th>
<td>
good first issue
</td>
</tr>
<tr>
<th>Assignees</th>
<td>
</td>
</tr>
<tr>
<th>Reporter</th>
<td>
scui-ibm
</td>
</tr>
</table>
<pre>
Here is a test case to illustrate the problem:
```
define signext i32 @afunc(ptr noalias nocapture dereferenceable(4) %.arg, ptr noalias nocapture dereferenceable(8) %.addr) {
entry:
%T_0 = alloca i32, align 4
%T_1 = alloca i32, align 4
%T_2 = alloca i32, align 4
%T_3 = alloca i32, align 4
%_arg_ = load i32, ptr %.arg, align 4
%_geq_0 = icmp sgt i32 %_arg_, -1
br i1 %_geq_0, label %if_then_1, label %if_else_1
if_then_1: ; preds = %entry
%_sub_1 = add nsw i32 %_arg_, -1
store i32 %_sub_1, ptr %T_3, align 4
call void @llvm.lifetime.start.p0(i64 4, ptr %T_1)
%_geq_1 = icmp sgt i32 %_sub_1, -1
br i1 %_geq_1, label %if_then_2, label %if_else_2
if_then_2: ; preds = %if_then_1
%_sub_2 = add nsw i32 %_sub_1, -1
call void @llvm.lifetime.start.p0(i64 4, ptr %T_0)
%_geq_2 = icmp sgt i32 %_sub_2, -1
br i1 %_geq_2, label %if_then_3, label %if_else_3
if_then_3: ; preds = %if_then_2
%_sub_3 = add nsw i32 %_sub_2, -1
%_call = call i32 @afunc.1(i32 %_sub_3, ptr nonnull %.addr)
br label %if_else_3
if_else_3: ; preds = %if_then_3, %if_then_2
%_addr_3 = load i64, ptr %.addr, align 8
%_conv_3 = ptrtoint ptr %T_0 to i32
%_sext_3 = sext i32 %_conv_3 to i64
%_equ_3 = icmp eq i64 %_addr_3, %_sext_3
br i1 %_equ_3, label %if_then_4, label %if_else_4
if_else_4: ; preds = %if_else_3
%_p2i_4 = ptrtoint ptr %T_0 to i32
%_zext_4 = zext i32 %_p2i_4 to i64
store i64 %_zext_4, ptr %.addr, align 8
call void @llvm.lifetime.end.p0(i64 4, ptr %T_0)
br label %if_else_2
if_else_2: ; preds = %if_else_4, %if_then_1
%_addr_2 = load i64, ptr %.addr, align 8
%_conv_2 = ptrtoint ptr %T_1 to i32
%_sext_2 = sext i32 %_conv_2 to i64
%_equ_2 = icmp eq i64 %_addr_2, %_sext_2
br i1 %_equ_2, label %if_then_4, label %if_else_41
if_else_41: ; preds = %if_else_2
%_p2i_41 = ptrtoint ptr %T_1 to i32
%_zext_41 = zext i32 %_p2i_41 to i64
store i64 %_zext_41, ptr %.addr, align 8
call void @llvm.lifetime.end.p0(i64 4, ptr %T_1)
br label %if_else_1
if_else_1: ; preds = %if_else_41, %entry
%_addr_1 = load i64, ptr %.addr, align 8
%_conv_1 = ptrtoint ptr %T_2 to i32
%_sext_1 = sext i32 %_conv_1 to i64
%_equ_1 = icmp eq i64 %_addr_1, %_sext_1
br i1 %_equ_1, label %if_then_4, label %if_else_42
if_else_42: ; preds = %if_else_1
ret i32 %_arg_
if_then_4: ; preds = %if_else_1, %if_else_2, %if_else_3
call void @_stop(ptr null, i32 -1, i32 11)
unreachable
}
declare void @_stop(ptr, i32, i32)
declare i32 @afunc.1(i32, ptr noalias nocapture dereferenceable(8))
declare void @llvm.lifetime.start.p0(i64 immarg, ptr nocapture)
declare void @llvm.lifetime.end.p0(i64 immarg, ptr nocapture)
```
With "`llc -O2 t.ll -print-after-all` ", it can be shown that `%stack.1.T_1` is merged with `%stack.0.T_0`, and thus marked dead.
Just before stack-coloring:
```
# *** IR Dump After Slot index numbering (slotindexes) ***:
# Machine code for function afunc: IsSSA, TracksLiveness
Frame Objects:
fi#0: size=4, align=4, at location [SP]
fi#1: size=4, align=4, at location [SP]
fi#2: size=4, align=4, at location [SP]
fi#3: size=4, align=4, at location [SP]
```
And after stack-coloring:
```
# *** IR Dump After Merge disjoint stack slots (stack-coloring) ***:
# Machine code for function afunc: IsSSA, TracksLiveness
Frame Objects:
fi#0: size=4, align=4, at location [SP]
fi#1: dead
fi#2: size=4, align=4, at location [SP]
fi#3: size=4, align=4, at location [SP]
```
For this test case, `%stack.1.T_1` and `%stack.0.T_0` cannot be merged. In the code, their addresses are compared, and should be different.
</pre>
<img width="1px" height="1px" alt="" src="http://email.email.llvm.org/o/eJzVWNtu2zgQ_Rr5hbAgUpIvD35w1gg2iy262BToo0GJtM2WlhySStp-_Q4p2ZZkKnEuC-wWbmTJM8OZM4eHpLKS_Vz8zhVHQiOKDNcG5VRzZEokpKy0UdTA3Y6jgyozyfdBvAyiVRAtg0nUfNwt4xtRcKTFtuA_DBIxQUES0U1V5AGZHYxCRUmloBquOT2YCsZkMPAG_hc5pxAb7JKAzFFA0pCqbUB-Q9f6zU5-jCn3fXpT58ULo36ekkbW6Ms6QkG8QlRKCGlTtUPBINsCJR07fKUdudIuvspuDcWvnaUsKTvaWShayHjctvyhqUzk-wPS26YNTUTrNcZHh0whgc9u9kdJMy7tI7FZQ8eLNe4_5VLzdROi_ns2jSHodf-C-AbYxJl2uULkuketSnSVHbFnDBX66ZlCtCktfZvfnWcLLsDcg1YOLUCPpWCWo1I-7kMpNtyIPQ-1ocqEBwBkJiYJuLRjQeR5H3HsR_yUyBDkF-A6HIkXcuKDnLwH8nPferATL-yeat6KYeTBkAxjSJ7D8AItV1PsxTD2YRh_BIakj2E8iGGvGvvY4Wjt3Ze2bobYAtjyjs-SWBSVlG3FawH0YunNww8o3WU0BIXNrMGiFrJJ0hEyl_hxbs46mJTFY-MJ1qYUhWkRyC1OcRd1WHMaB31afs6BrMOko5X8oWrsHev4gzVoZd3U1QS-ZJ_z97Iv8bIv8bUgeWcL2s2tyzoQsU5egdsvW17t8KuNWx2nC1sjtA1MtecV_XxGJ3jBrlEJH6X7itg8_AA8kx6l8QWlyZspTQZag4coTQYoTQYoTYYpTTqUJn5K-wV1gNL9jcDx6dVNGOwBueA0fgVyNTXxAKvxFbTG_xqv8Qu89mL6rs1VqzE1AS52W44e-M2kHmoNGSI1HiB1vzNHUuJhUuMOqT27BOf_GlJ7hSV5hbIMNuCUneK9jblnY_IhSwM-S1kzrbr3sZfLa5gRh-OZDXYZ1smmO8bHb7jN4qpQnOY7dxCrC5mu2hUxnksKM8wTvol3usy7Hr690GsPhRdBr9qxiv2-cwBtxrgyWGf6vxSqd4yu_34VZgeNIvBYyhyh8WeYTCH0aHxQMMfGdGO4GkPTwMDZQXgk7NG9QBkcwnflUwGHdmqQDUxSKC__HuLQ6g94wFl_z9WWM_TkBmrZRKFdeyfuPEgLBkEqMKbqOxgzTlnYTvOPShsYb2MF1LmP81KWkOF26C1BQGDTRZb1B939jVYVzOqlLQfdyxLmRcH4D6DdPuM2DhjPNDx3j7muT_mN-3kMCPoJKGjfP-Ql4wgSQpY0RpQFql9BwGy60_f3S1vXFwWp6j_FIy-41nWMW0X3HH3OvvHc6Nbrgo2A6JF11-IXh_mVnKTwdGOQPc-7wYL05v6vIF113PH73Mn73OM3unuJuQRKOPJ9QL8_WQoiJvQ3t264gMg2W7uud-P_fxtvZ81_tp-3AJjZgR6c3vy5JcInGlYNfEphRacorQ40ohKiu8K9MbQtseHgu1D2OKwAda6RVc683B_gyo46A5JVSWaDMLFxMm4aqRnxBZ5MYhxF0_lsxBYxm8dzOjLCSL6AEntESWGnUOSlUtDPFqdcbvD7qFJysTPm4HpNbuGzBQ2sshAyghur5M0FtLa0rIBboXVl1ec2nU5JOtotJnQSz6Ypw_M4TRnL4iiPMJlm03nGeJRPR25joW1-IM_bsmTQPAUQu0hWsdPVSCxIREg0xzFcIV5IMM3TBPOUpCzK8whWFr6nQoZufSnVdqQWLrOs2mq77Aht9PlHqt3bV4eKjU8rsyvVQueVGItsP3JjL1wJ_wDABS5g">