Issue |
90019
|
Summary |
[mlir][bufferization] linalg.map in loops bufferize error
|
Labels |
mlir
|
Assignees |
|
Reporter |
Artorias123
|
We have found that linalg.map in the loop may produce incorrect results in certain specific scenarios when using one-shot-bufferize.
```
func.func private @f(%arg: tensor<32x1xf32>) -> ()
func.func @test(%arg0: i32, %arg2: tensor<32x1xf32>, %arg3: tensor<32x1xf32>) {
%cst_0 = arith.constant 0.000000e+00 : f32
%c0_i32 = arith.constant 0 : i32
%c1_i32 = arith.constant 1 : i32
%0 = tensor.empty() : tensor<32x1xf32>
%1 = linalg.fill ins(%cst_0 : f32) outs(%0 : tensor<32x1xf32>) -> tensor<32x1xf32>
scf.for %arg1 = %c0_i32 to %arg0 step %c1_i32 : i32 {
%2 = linalg.map { arith.subf } ins(%1, %arg2 : tensor<32x1xf32>, tensor<32x1xf32>) outs(%0 : tensor<32x1xf32>)
%3 = tensor.empty() : tensor<32x1xf32>
%4 = linalg.map { arith.subf } ins(%2, %arg3 : tensor<32x1xf32>, tensor<32x1xf32>) outs(%3 : tensor<32x1xf32>)
func.call @f(%4) : (tensor<32x1xf32>) -> ()
}
return
}
```
This IR will be bufferized into the following form:
```
// ./bin/mlir-opt -one-shot-bufferize -allow-unregistered-dialect bufferize_test.mlir
module {
func.func private @f(tensor<32x1xf32>)
func.func @test(%arg0: i32, %arg1: tensor<32x1xf32>, %arg2: tensor<32x1xf32>) {
%0 = bufferization.to_memref %arg2 : memref<32x1xf32, strided<[?, ?], offset: ?>>
%1 = bufferization.to_memref %arg1 : memref<32x1xf32, strided<[?, ?], offset: ?>>
%cst = arith.constant 0.000000e+00 : f32
%c0_i32 = arith.constant 0 : i32
%c1_i32 = arith.constant 1 : i32
%alloc = memref.alloc() {alignment = 64 : i64} : memref<32x1xf32>
linalg.fill ins(%cst : f32) outs(%alloc : memref<32x1xf32>)
scf.for %arg3 = %c0_i32 to %arg0 step %c1_i32 : i32 {
linalg.map { arith.subf } ins(%alloc, %1 : memref<32x1xf32>, memref<32x1xf32, strided<[?, ?], offset: ?>>) outs(%alloc : memref<32x1xf32>)
%alloc_0 = memref.alloc() {alignment = 64 : i64} : memref<32x1xf32>
linalg.map { arith.subf } ins(%alloc, %0 : memref<32x1xf32>, memref<32x1xf32, strided<[?, ?], offset: ?>>) outs(%alloc_0 : memref<32x1xf32>)
%2 = bufferization.to_tensor %alloc_0 : memref<32x1xf32>
func.call @f(%2) : (tensor<32x1xf32>) -> ()
}
return
}
}
```
The %alloc is modified in each iteration, but semantically in the original graph, the result of %1 should be the fixed output of fill and should not be modified. Therefore, it seems that there is an issue with the bufferization here.
_______________________________________________
llvm-bugs mailing list
llvm-bugs@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-bugs