<table border="1" cellspacing="0" cellpadding="8">
    <tr>
        <th>Issue</th>
        <td>
            <a href=https://github.com/llvm/llvm-project/issues/62249>62249</a>
        </td>
    </tr>

    <tr>
        <th>Summary</th>
        <td>
            [mlir][linalg-detensorize] Entry block arg types get converted.
        </td>
    </tr>

    <tr>
      <th>Labels</th>
      <td>
            new issue
      </td>
    </tr>

    <tr>
      <th>Assignees</th>
      <td>
      </td>
    </tr>

    <tr>
      <th>Reporter</th>
      <td>
          silvasean
      </td>
    </tr>
</table>

<pre>
    
Running:
```
mlir-opt --pass-pipeline='builtin.module(func.func(linalg-detensorize))' repro.mlir
```
Gives the following error:

```
repro.mlir:3:3: error: 'func.func' op type of entry block argument #0('f32') must match the type of the corresponding argument in function signature('tensor<f32>')
```

Full error log:
https://gist.github.com/silvasean/73150502029639c261620bae4c8035f4

```
#map = affine_map<() -> ()>
module {
  func.func @main(%arg0: tensor<f32>) -> tensor<f32> {
    %0 = tensor.empty() : tensor<f32>
    %1 = linalg.generic {indexing_maps = [#map, #map], iterator_types = []} ins(%arg0 : tensor<f32>) outs(%0 : tensor<f32>) {
    ^bb0(%in: f32, %out: f32):
 linalg.yield %in : f32
    } -> tensor<f32>
    cf.br ^bb1(%1 : tensor<f32>)
  ^bb1(%2: tensor<f32>):  // pred: ^bb0
    return %2 : tensor<f32>
  }
}
```

So in plain English the pass ends up changing the function entry block's arg type (from `tensor<f32>` to `f32`) is wrong because the pass [deliberately does not change function signatures](https://github.com/llvm/llvm-project/blob/a080798fb2d2343704512ad6adbf9fe1e13eec96/mlir/lib/Dialect/Linalg/Transforms/Detensorize.cpp#L496-L500), and specifically avoids modifying the entry block.

This seems to be some spooky action at a distance in the dialect conversion framework. Essentially what seems to happen is that:

1. [FunctionNonEntryBlockConversion](https://github.com/llvm/llvm-project/blob/a080798fb2d2343704512ad6adbf9fe1e13eec96/mlir/lib/Dialect/Linalg/Transforms/Detensorize.cpp#L97) converts the non-entry block, [registering](https://github.com/llvm/llvm-project/blob/a080798fb2d2343704512ad6adbf9fe1e13eec96/mlir/lib/Transforms/Utils/DialectConversion.cpp#L1328) the [DetensorizeTypeConverter](https://github.com/llvm/llvm-project/blob/a080798fb2d2343704512ad6adbf9fe1e13eec96/mlir/lib/Dialect/Linalg/Transforms/Detensorize.cpp#L140) as the type converter for the func.func's region
2. [DetensorizeGenericOp](https://github.com/llvm/llvm-project/blob/a080798fb2d2343704512ad6adbf9fe1e13eec96/mlir/lib/Dialect/Linalg/Transforms/Detensorize.cpp#L64) inlines the body of the linalg.generic, which triggers [OperationLegalizer::legalizePatternBlockActions](https://github.com/llvm/llvm-project/blob/a080798fb2d2343704512ad6adbf9fe1e13eec96/mlir/lib/Transforms/Utils/DialectConversion.cpp#L2005) which then [calls convertBlockSignature](https://github.com/llvm/llvm-project/blob/a080798fb2d2343704512ad6adbf9fe1e13eec96/mlir/lib/Transforms/Utils/DialectConversion.cpp#L2028) on the entry block (which is the block that the body was inlined into).

I'm really not sure what the right solution is here. One thing that is not clear to me is why the dialect conversion framework wants to change the block arg types of the destination block of inlining. That definitely seems very undesirable in this case.
</pre>
<img width="1px" height="1px" alt="" src="http://email.email.llvm.org/o/eJzUV09v474R_TT0ZWCBoizJOviQxPEPBYJu0U3PC0oaSexSpEBScb2fviAp_0nq3WJPiwCOI8nD4byZN_Mobq3oFeKO5I8k36_47AZtdlbIN26Rq1Wt29OO0D2hD_-clRKqJ9lDvCcFXT7hdpTCrPXkYL2euLXrSUwohUKS7Qkr61lIJ1Qy6naWSNi2m1WT-C_CtlIoLvt1iw6V1Ub8QMKq8CnB4GR04p3f3fUv8YYW3IDQaSn1Uage0BhtrmHeW3bjNXvIlr_LQiCsvImvBD2BO00IugNUzpyglrr5Dtz084jKAWEZJWzrl2WMsJKwCsbZOhi5a4YQ3nm9v260MWgnrVof7sWLUOA3dEIr8GXhbjYY3cbEkOzJ-8-e4xZ3kcXvwyxlhANSX0s2ODdZf8cOhB16YV3SCzfMddLokbDDpe6EHcoszWlOGWVVkVUNK9KC0ZrjptnSLO82v8guYdnIJyDZHnjXCYXfRj6R7ClgqWBNsmeI1x5LZE_gBZDyMd4DXAoAZENHLlRYkXPTU1-i_8nI4vfD81uPAITlNIQVrRIcJ3daorrn9HZhGhZGqiY9KjSi8d6FavE_QvUeow02vpdCBgh7guUq3_sb4dBwp803z4arcb4n5R6EsleId8NhFejZLVY_NXmPOH-u68jNXCi_IjDUx5Xr2V0eVBeOnCGeBMoWwjI4m13dlvu76b5aNF1Sm7h9GrdPfxLwec2tLfuJaebtAnlhMtiGXo0ILxsbdLNRPnD2q5qScr-Q9XJxr5G-at-Wk-RCwbPqpbCxnf2IA1SthXmCZuCq960c5tC5hW8mBWGl9X0ep4CffkaPQAr6MbiCgtP-B39fUF9OYeFotOqhxobPFq_bk_yxRSlqzymUJ2g1WlDaxXjwzjCxgYfbj2PgZgJI-Xb-t56M_jc2jrBDLXVN2IHTLS2rbVezlmWbrKSbPGW8LXhbd1WHKaYZYlMVhB3CaGUHKfy6veAyOnoJ3CLs8Gq4sp02o_W_Xwd_0kwTYdnLpirWLzmlQQWegKsW7ISN6ETDpTwBf9OitTDqVnSnc-pvMp7cFvF1EBYs4mh9dmsEq0cEO2n9_QQ85og74NAK67hq0NfcO2xj4NBo9YbGervO8BGP2nxP4NlaVE6EeI4Dd9ctBj5NqHzp3MDdBylKE1-5w1Kcv2v17MN-9FE_Xfb5NIWqgtjFBLmoxEqr9TvyP3nABr3eoPFHiD8C7h2Sfzkh7RXxNfFnXGkWZcEDIvnjDfLX04TR3qH5NHVKN2GacHs9jTRnENBpc5ld50OPBV8xrSJpWfIhC39FBfwyfZoMFJswTpU_lMYs-MPt-Uz2Xtg9Z4-D8Gc3I_oeTZi2XyY_aoVWL9hzKX5gOGVmD3K5_Qd3Do0KrfwQuvsPDdzfozqjNPepWQAPqDxYP2ftmSMB0tfLmfRTgIr9q9VHafD6G6GKhQbhqZ_UV1YcuV2o0oJQThNWvZOUvxFWjmAwDH-vuXY2GFXA-zCiHxxYLecgLsLCgAYT-KK8fke94s4_D3otkRuvGyMGuR9O_1d94MiVC1qziP0VyPmcYc_UbtE6oQJxFxPdRXBC9Qm8-kha7IQS4RgRVewNzQlm1aIVhtdykURhoeEWk1W7y9oqq_gKd2mxTas82xRsNezKqmi3TdUU25SnrC6aGnmedrwpeL1NN2wldoyyjG4YpWlablhCabHlaZbTrqZFV9dkQ3HkQiaePYk2_UpYO-OuYGxTrSSvUdrwusqYwiOEHwlj_u3V7ALj6rm3ZEOlsM5evTjhZHjPDaTK9yR_vPPeme_h-f0b3pLLHt1lYLbJajZy99sNEGL1rA1Y_hsAAP__Q6jcTQ">