<table border="1" cellspacing="0" cellpadding="8">
<tr>
<th>Issue</th>
<td>
<a href=https://github.com/llvm/llvm-project/issues/100146>100146</a>
</td>
</tr>
<tr>
<th>Summary</th>
<td>
arith.floordivsi won't lower to llvm with vector.load'ed vectors
</td>
</tr>
<tr>
<th>Labels</th>
<td>
</td>
</tr>
<tr>
<th>Assignees</th>
<td>
</td>
</tr>
<tr>
<th>Reporter</th>
<td>
alankarmisra
</td>
</tr>
</table>
<pre>
In the following example, I arith.addi and arith.floordivsi with constant vectors and vectors loaded from a memref. The add will succeed in lowering to llvm in both situations but floordivsi fails to lower to llvm with vectors loaded from memrefs for some reason.
```mlir
module @bug {
func.func @main() {
%number = arith.constant dense<10> : vector<1xi32>
%resolved_floordivsi = arith.floordivsi %number, %number : vector<1xi32>
%alloca = memref.alloca() : memref<1xi32>
%idx = arith.constant 0 : index
vector.store %number, %alloca[%idx] : memref<1xi32>, vector<1xi32>
%loadedNum = vector.load %alloca[%idx] : memref<1xi32>, vector<1xi32>
%unresolved_floordivsi = arith.floordivsi %loadedNum, %number: vector<1xi32>
vector.print %resolved_floordivsi : vector<1xi32>
vector.print %unresolved_floordivsi : vector<1xi32>
%resolved_add = arith.addi %number, %number : vector<1xi32>
%resolved_add_too = arith.addi %loadedNum, %number : vector<1xi32>
vector.print %resolved_add : vector<1xi32>
vector.print %resolved_add_too : vector<1xi32>
return
}
}
```
Running
```bash
mlir-opt input.mlir \
-lower-affine \
-convert-vector-to-llvm \
-convert-arith-to-llvm \
-convert-func-to-llvm \
-convert-index-to-llvm \
--convert-to-llvm \
-o out.mlir
```
gives me
```mlir
module @bug {
llvm.func @main() {
%0 = llvm.mlir.constant(dense<20> : vector<1xi32>) : vector<1xi32>
%1 = llvm.mlir.constant(0 : index) : i64
%2 = builtin.unrealized_conversion_cast %1 : i64 to index
%3 = llvm.mlir.constant(dense<10> : vector<1xi32>) : vector<1xi32>
%4 = llvm.mlir.constant(dense<1> : vector<1xi32>) : vector<1xi32>
%5 = llvm.mlir.constant(1 : index) : i64
%6 = llvm.mlir.constant(1 : index) : i64
%7 = llvm.alloca %5 x i32 : (i64) -> !llvm.ptr
%8 = llvm.mlir.undef : !llvm.struct<(ptr, ptr, i64, array<1 x i64>, array<1 x i64>)>
%9 = llvm.insertvalue %7, %8[0] : !llvm.struct<(ptr, ptr, i64, array<1 x i64>, array<1 x i64>)>
%10 = llvm.insertvalue %7, %9[1] : !llvm.struct<(ptr, ptr, i64, array<1 x i64>, array<1 x i64>)>
%11 = llvm.mlir.constant(0 : index) : i64
%12 = llvm.insertvalue %11, %10[2] : !llvm.struct<(ptr, ptr, i64, array<1 x i64>, array<1 x i64>)>
%13 = llvm.insertvalue %5, %12[3, 0] : !llvm.struct<(ptr, ptr, i64, array<1 x i64>, array<1 x i64>)>
%14 = llvm.insertvalue %6, %13[4, 0] : !llvm.struct<(ptr, ptr, i64, array<1 x i64>, array<1 x i64>)>
%15 = llvm.mlir.constant(0 : i64) : i64
%16 = llvm.extractelement %3[%15 : i64] : vector<1xi32>
%17 = llvm.extractvalue %14[1] : !llvm.struct<(ptr, ptr, i64, array<1 x i64>, array<1 x i64>)>
%18 = llvm.getelementptr %17[%1] : (!llvm.ptr, i64) -> !llvm.ptr, i32
llvm.store %16, %18 : i32, !llvm.ptr
%19 = llvm.extractvalue %14[1] : !llvm.struct<(ptr, ptr, i64, array<1 x i64>, array<1 x i64>)>
%20 = llvm.getelementptr %19[%1] : (!llvm.ptr, i64) -> !llvm.ptr, i32
%21 = llvm.load %20 : !llvm.ptr -> i32
%22 = llvm.mlir.undef : vector<1xi32>
%23 = llvm.mlir.constant(0 : i32) : i32
%24 = llvm.insertelement %21, %22[%23 : i32] : vector<1xi32>
%25 = llvm.shufflevector %24, %22 [0] : vector<1xi32>
%26 = arith.floordivsi %25, %3 : vector<1xi32>
vector.print %4 : vector<1xi32>
vector.print %26 : vector<1xi32>
%27 = llvm.add %25, %3 : vector<1xi32>
vector.print %0 : vector<1xi32>
vector.print %27 : vector<1xi32>
llvm.return
}
}
```
%4 is the result for the first arith.floordivsi for (10, 10) and correctly folds to 1
%26 is the result for the second arith.floordivsi and does not lower to llvm
%0 is the result for the first arith.add for (10, 10) and correctly folds to 20
%27 is the result for the second arith.add and lowers to llvm.add
```bash
mlir-opt --version
Homebrew LLVM version 18.1.8
Optimized build.
```
</pre>
<img width="1px" height="1px" alt="" src="http://email.email.llvm.org/o/eJzMWFGP4yYQ_jXkBSUyYDvJQx42u7fqSddWqqq-rojBCS2GCHB2r7--AmPHSewke3fdVlplkzHzzTfD8GGg1oqt4nwFsjXInia0djttVlRS9Rc1lbCGTjaafV19VtDtOCy1lPpVqC3kb7TaSw7wI_wMqRFuN6OMCUgViz9LqbVh4mAFfBVuBwutrKPKwQMvnDY2DG2_S00ZZ7A0uoIUVrwyvJzB33ccUsbgq5AS2rooOGdQKCj1KzeehdNQykPlbRvtdtAKV1MntLJwUzvYo1BSIW0Y7307x8BsiERDwcJSG2h1xaHh1Go1A8kTSB7iZ540f5UUpjFVmtWSQ5Amm3oLwXzdmGFZq2LmP_yjigoF8ALgZW8EhBDgTNXVhhsIyFOsYlc1xpXlgDyiBJBPEJCHSNub3gTBgHw6QTLcanng7KVXhCNs39hG9XPZp3ArApVSFzSAxglrLG1q5CHaxwAEexvKNAmuQjH-dhzeUJlZpw2_oBzjZusGFGRPI9Hx442cmhb4pa4CsRjUG39smFq9Z3o6UiczNDhBAf-8aHsjlBvviavzfA4xxvzudvTr-Zho0Ixv7sA-6IvTegB4uHbvzfqM_Tf7RpLj_oa72qgWDMyfotJ0X1rJ6evQb7VSQm0HpWlD7S5KkxRmqvcOCrWv3cz_hCB7jLGmQRentCyF4n17odWBGzdtGE-dngbhHBgRCn9tgNe_a8_Dkh8a0I0YeKahjtlEy1mJ2uWwFQduYcVPrQMSDsc0POwY94h4EvowjPawnbIBvGhVHF9R8aid11sfjcfo62fEEnl64o2D96YW0gk182uaSvE3Zy9Noa3Q6qWg1rWRAoLfNM9UGeCM3E722pZ1V7LpHTG-M0Q2HgLdrmf-Xd7zo3e7p3pCb1AQHBwAXngfvITTkCZGYfDemROcxRmLWjFeRoDGwzpTFw6QR4AX3hs_wvgv4D9Cagz96mvko-dp3MyGrMvzCi6P0YWy3LgDlXXYq-dRexcgWyftrvkvUYKnqyS5SWoJsjX6WFLft3YRHs0JoZgUSkC2xh-bFRmllbWsMMjWxP_44C5IR6nlLTUCsnX6H1C7ojtJN_1jndCTHf7mDC0cl7zizXsHaV5UQ4TGNyZ2Y2OZX4Ae-yv9-MXSE7Utb_PbO9NwjTkeKS364thSGNBN_4jgGCqmEY8WqGuKRVM6ghvDsOqi5f-qYDi5VrDljylYDNUTsvaMhJOTVH3cAHXhi0c3q-v9ia-8cCTH-Vp2X0-cL5Sgt2Bwq54YN1UKoRqQu5YO7i1mu6vLUvLGoQndocP-Pnh5hDvFzEePhbjVVfLeI0n6XofA4mb6_fcYxs4ovjdkctXhguD8Fn6g9d7jlS-VsOHqy3BbSxfug8JNmDDWXU5LGSZ7gRKft_9chmuuQhvDCye_wlJLFu6hUBcC5yMxLC_00HWaR2SaW6i0O73P6jCTO2j7ObqfLz7WBM_vIezhPVYgaFuG3nzvQXU6jWeRxv6TrvjG8Ff45csfP8P4CKLFDM0W7ZT-unei8ieZcLhhs7MgE7YibEmWdMJXaI7RPEOY4MluhWjOeZYjhDDCyzyleV7klFFUlIwTgiZihROcJnNMUI5IhmcMkdwPwguSJpssB2nCKyrkLGSpzXYirK35CiUJSvOJpBsubXvPalZ-1HRTby1IEymss0c_J5zkq8tLVK0AnrvxC8ygwQDPeXetOqmNXO2c21tAHgB-Bvh5K9yu3swKXQH8HFqm-TfdG_0nLxzAz4G3Bfg5Uj-s8D8BAAD__1UhYV0">