[flang-commits] [flang] [flang][MLIR][OpenMP] Extend delayed privatization for arrays (PR #85023)
Kareem Ergawy via flang-commits
flang-commits at lists.llvm.org
Thu Apr 18 01:55:06 PDT 2024
ergawy wrote:
> Thank you for the patch. I was trying to understand the changes with simpler examples of the form:
>
> ```
> program main
> implicit none
> integer :: i
> real, dimension(5) :: array
>
> !$omp parallel private(array)
> array(2) = array(2) + 10
> !$omp end parallel
> end program
> ```
>
> It turns out that with `-mmlir --openmp-enable-delayed-privatization` flag, we get the following verification failure:
>
> ```
> error: loc("/home/user1/.llvm/test/par.f90":4:27): 'hlfir.declare' op of array entity with a raw address base must have a shape operand that is a shape or shapeshift
> error: loc("/home/user1/.llvm/test/par.f90":4:27): 'fir.shape' op using value defined outside the region
> error: loc("/home/user1/.llvm/test/par.f90":4:27): 'hlfir.declare' op of array entity with a raw address base must have a shape operand that is a shape or shapeshift
> ```
>
> I am not completely sure what went wrong here.
After debugging this for a bit, it seems the issue only happens if we use the default lower bound (i.e. if we do not specify an explicit non-default lower bound for the array). For example, the issue does not happen if you change the example you provided to the following:
```
program main
implicit none
integer :: i
real, dimension(2:6) :: array
!$omp parallel private(array)
array(2) = array(2) + 10
!$omp end parallel
end program
```
Looking at the IR, it seems flang generates the `hlfir.declare` op differently for the `dimension(5) :: array` case vs the `dimension(2:6) :: array` case.
For `dimension(5) :: array`, the following `hlfir.declare` op is generated:
```mlir
%3:2 = "hlfir.declare"(%1, %2) <{operandSegmentSizes = array<i32: 1, 1, 0>, uniq_name = "_QFEarray"}>
: (!fir.ref<!fir.array<5xf32>>, !fir.shape<1>)
-> (!fir.ref<!fir.array<5xf32>>, !fir.ref<!fir.array<5xf32>>)
```
For `dimension(2:6) :: array`, the following `hlfir.declare` op is generated:
```mlir
%4:2 = "hlfir.declare"(%2, %3) <{operandSegmentSizes = array<i32: 1, 1, 0>, uniq_name = "_QFEarray"}>
: (!fir.ref<!fir.array<5xf32>>, !fir.shapeshift<1>)
-> (!fir.box<!fir.array<5xf32>>, !fir.ref<!fir.array<4xf32>>)
```
In the first case (i.e. `dimension(5) :: array`), note that `hlfir.declare` returns an **unboxed** value: it returns a direct reference to the array. In the second case, `hlfir.declare` returns a **boxed** value which is what we need here.
For me (and take this with a grain of salt since I didn't work on this part of the code base before) this seems like a bug in how `hlfir.declare` is generated: I think we should box the value regardless of whether it has the default or a non-default lower bound specified for the array.
@jeanPerier I think you will have a more informed input here. Can you please take a look and let me know what you think?
https://github.com/llvm/llvm-project/pull/85023
More information about the flang-commits
mailing list