[llvm] [CVP] Improve the value solving of select at use (PR #76700)

Yingwei Zheng via llvm-commits llvm-commits at lists.llvm.org
Sat Jan 6 06:08:26 PST 2024


dtcxzyw wrote:

Hi @nikic! I think I have figured out how to fix the [regression](https://github.com/dtcxzyw/llvm-opt-benchmark/pull/83#issuecomment-1873701727) caused by this patch.

Here is the reduced IR:
```
define void @test_icmp_with_abs_loop(i16 %a, i16 %b) {
  %abs = call i16 @llvm.abs.i16(i16 %a, i1 false)
  %cmp1 = icmp slt i16 %a, 0
  %cmp2 = icmp eq i16 %abs, 1
  %or = select i1 %cmp1, i1 true, i1 %cmp2
  call void @use(i1 %or)
  br i1 %or, label %exit, label %if.then
if.then:
  %cmp3 = icmp ult i16 %a, %b
  call void @use(i1 %cmp3)
  br i1 %cmp3, label %for.body, label %exit
for.body:
  %indvar = phi i32 [0, %if.then], [%indvar.next, %for.body]
  %indvar.next = add i32 %indvar, 1
  %cmp5 = icmp ult i32 %indvar.next, 10
  br i1 %cmp5, label %for.body, label %if.then2
if.then2:
  %cmp4 = icmp ult i16 %abs, %b
  call void @use(i1 %cmp4)
  br label %exit
exit:
  ret void
}
declare i16 @llvm.abs.i16(i16, i1)
declare void @use(i1)

```
`%cmp4 = icmp ult i16 %abs, %b` always evaluates to true because `%abs == %a` and `%a <u %b`.
I tried to replace the abs at use in CVP. But it only worked with the cases without loops:
```
define void @test_icmp_with_abs(i16 %a, i16 %b) {
  %abs = call i16 @llvm.abs.i16(i16 %a, i1 false)
  %cmp1 = icmp slt i16 %a, 0
  %cmp2 = icmp eq i16 %abs, 1
  %or = select i1 %cmp1, i1 true, i1 %cmp2
  call void @use(i1 %or)
  br i1 %or, label %exit, label %if.then
if.then:
  %cmp3 = icmp ult i16 %a, %b
  call void @use(i1 %cmp3)
  br i1 %cmp3, label %if.then2, label %exit
if.then2:
  %cmp4 = icmp ult i16 %abs, %b ; %abs will be replaced with %a
  call void @use(i1 %cmp4)
  br label %exit
exit:
  ret void
}
declare i16 @llvm.abs.i16(i16, i1)
declare void @use(i1)

```

After further investigation I have found `solveBlockValueNonLocal` failed to given the range of `%a` at `%if.then2` due to the existence of an unrelated loop.

The debug output shows that we hit a cycle and exit early. But I think at least we can infer some information from the idom `%if.then` :(
https://github.com/llvm/llvm-project/blob/4b9bbd38686af3dbffd45b360bd5af629426bdbc/llvm/lib/Analysis/LazyValueInfo.cpp#L712-L737

DomTree info is unavailable for LVI because the analysis is also used by `LowerSwitch` and `JumpThreading`, which don't update DomTree eagerly.
Could you please give me some suggestions on how to address this problem?
If not, I will fix this issue in ConstraintElimination.


https://github.com/llvm/llvm-project/pull/76700


More information about the llvm-commits mailing list