diff --git a/mlir/include/mlir/Dialect/Affine/IR/AffineOps.h b/mlir/include/mlir/Dialect/Affine/IR/AffineOps.h index 7c950623f77f4..72cf86afae187 100644 --- a/mlir/include/mlir/Dialect/Affine/IR/AffineOps.h +++ b/mlir/include/mlir/Dialect/Affine/IR/AffineOps.h @@ -15,6 +15,7 @@ #define MLIR_DIALECT_AFFINE_IR_AFFINEOPS_H #include "mlir/Dialect/Affine/IR/AffineMemoryOpInterfaces.h" +#include "mlir/Dialect/Affine/IR/AffineTraits.h" #include "mlir/Dialect/Arith/IR/Arith.h" #include "mlir/Dialect/Utils/StaticValueUtils.h" #include "mlir/IR/AffineMap.h" diff --git a/mlir/include/mlir/Dialect/Affine/IR/AffineOps.td b/mlir/include/mlir/Dialect/Affine/IR/AffineOps.td index c79a1ea301d44..0e6391ab4251a 100644 --- a/mlir/include/mlir/Dialect/Affine/IR/AffineOps.td +++ b/mlir/include/mlir/Dialect/Affine/IR/AffineOps.td @@ -13,6 +13,7 @@ #ifndef AFFINE_OPS #define AFFINE_OPS +include "mlir/Dialect/Affine/IR/AffineTraits.td" include "mlir/Dialect/Arith/IR/ArithBase.td" include "mlir/Dialect/Affine/IR/AffineMemoryOpInterfaces.td" include "mlir/Interfaces/ControlFlowInterfaces.td" diff --git a/mlir/include/mlir/Dialect/Affine/IR/AffineTraits.h b/mlir/include/mlir/Dialect/Affine/IR/AffineTraits.h new file mode 100644 index 0000000000000..a2908b3636184 --- /dev/null +++ b/mlir/include/mlir/Dialect/Affine/IR/AffineTraits.h @@ -0,0 +1,27 @@ +//===- AffineTraits.h - MLIR Affine Traits --------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file defines traits brought in by the Affine dialect. +// +//===----------------------------------------------------------------------===// +#ifndef AFFINE_TRAITS_H +#define AFFINE_TRAITS_H + +#include "mlir/IR/OpDefinition.h" + +namespace mlir::OpTrait { + +template +class AffineDim : public TraitBase { +public: + static LogicalResult verifyTrait(Operation *op) { return success(); } +}; + +} // namespace mlir::OpTrait + +#endif // AFFINE_TRAITS_H diff --git a/mlir/include/mlir/Dialect/Affine/IR/AffineTraits.td b/mlir/include/mlir/Dialect/Affine/IR/AffineTraits.td new file mode 100644 index 0000000000000..96b04fb674277 --- /dev/null +++ b/mlir/include/mlir/Dialect/Affine/IR/AffineTraits.td @@ -0,0 +1,25 @@ +//===- AffineTraits.td - Affine dialect traits -------------*- tablegen -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// Defines traits brought in by the MLIR Affine dialect. +// +//===----------------------------------------------------------------------===// +#ifndef AFFINE_TRAITS +#define AFFINE_TRAITS + +include "mlir/IR/OpBase.td" + +// Trait to declare that an op result is an affine dimension identifier. +// Prevents the result from being seen as a symbol into AffineMaps +// and IntegerSets. +// This is a deviation from upstream to consider linalg.index as +// a dimension rather than a symbol. See this PR: +// https://github.com/Xilinx/llvm-project/pull/537 +def AffineDim : NativeOpTrait<"AffineDim">; + +#endif // AFFINE_TRAITS diff --git a/mlir/include/mlir/Dialect/Linalg/IR/Linalg.h b/mlir/include/mlir/Dialect/Linalg/IR/Linalg.h index 85f5ebeb8081e..cb046baead87b 100644 --- a/mlir/include/mlir/Dialect/Linalg/IR/Linalg.h +++ b/mlir/include/mlir/Dialect/Linalg/IR/Linalg.h @@ -10,6 +10,7 @@ #define MLIR_DIALECT_LINALG_IR_LINALG_H #include "mlir/Bytecode/BytecodeOpInterface.h" +#include "mlir/Dialect/Affine/IR/AffineTraits.h" #include "mlir/Dialect/Utils/ReshapeOpsUtils.h" #include "mlir/Dialect/Utils/StructuredOpsUtils.h" #include "mlir/IR/AffineExpr.h" diff --git a/mlir/include/mlir/Dialect/Linalg/IR/LinalgOps.td b/mlir/include/mlir/Dialect/Linalg/IR/LinalgOps.td index e42fd5d2ce13c..62ffb6ad19e13 100644 --- a/mlir/include/mlir/Dialect/Linalg/IR/LinalgOps.td +++ b/mlir/include/mlir/Dialect/Linalg/IR/LinalgOps.td @@ -13,6 +13,7 @@ #ifndef LINALG_OPS #define LINALG_OPS +include "mlir/Dialect/Affine/IR/AffineTraits.td" include "mlir/Dialect/Linalg/IR/LinalgBase.td" include "mlir/Dialect/Linalg/IR/LinalgInterfaces.td" include "mlir/Interfaces/ControlFlowInterfaces.td" @@ -46,7 +47,7 @@ def Linalg_YieldOp : Linalg_Op<"yield", [Pure, ReturnLike, Terminator]>, let hasVerifier = 1; } -def Linalg_IndexOp : Linalg_Op<"index", [Pure]>, +def Linalg_IndexOp : Linalg_Op<"index", [Pure, AffineDim]>, Arguments<(ins ConfinedAttr]>:$dim)>, Results<(outs Index:$result)> { let summary = "linalg index operation"; diff --git a/mlir/lib/Dialect/Affine/IR/AffineOps.cpp b/mlir/lib/Dialect/Affine/IR/AffineOps.cpp index c95899d817eac..0896e7ef51e56 100644 --- a/mlir/lib/Dialect/Affine/IR/AffineOps.cpp +++ b/mlir/lib/Dialect/Affine/IR/AffineOps.cpp @@ -8,6 +8,7 @@ #include "mlir/Dialect/Affine/IR/AffineOps.h" #include "mlir/Dialect/Affine/IR/AffineValueMap.h" +#include "mlir/Dialect/Linalg/IR/Linalg.h" #include "mlir/Dialect/MemRef/IR/MemRef.h" #include "mlir/Dialect/UB/IR/UBOps.h" #include "mlir/Dialect/Utils/StaticValueUtils.h" @@ -312,6 +313,10 @@ bool mlir::affine::isValidDim(Value value, Region *region) { return isa(parentOp); } + // Remove me: linalg.index ops are valid affine dim identifiers + if (op->hasTrait()) + return true; + // Affine apply operation is ok if all of its operands are ok. if (auto applyOp = dyn_cast(op)) return applyOp.isValidDim(region); @@ -439,6 +444,10 @@ bool mlir::affine::isValidSymbol(Value value, Region *region) { return false; } + // Remove me: linalg.index ops are not valid affine symbols + if (defOp->hasTrait()) + return false; + // Constant operation is ok. Attribute operandCst; if (matchPattern(defOp, m_Constant(&operandCst))) diff --git a/mlir/test/Dialect/Linalg/affine-if.mlir b/mlir/test/Dialect/Linalg/affine-if.mlir new file mode 100644 index 0000000000000..03910c8138341 --- /dev/null +++ b/mlir/test/Dialect/Linalg/affine-if.mlir @@ -0,0 +1,30 @@ +// RUN: mlir-opt -canonicalize %s | FileCheck %s + +// Check that linalg.index does not cause folding of affine.if set to +// a symbolic set. +// This is a deviation from upstream MLIR. +// The origin of this test is that PR: +// https://github.com/Xilinx/llvm-project/pull/537 + +// CHECK: = affine_set<(d0) : (-d0 + 5 >= 0)> +#set = affine_set<(d0) : (-d0 + 5 >= 0)> + +func.func @linalg_index_affine_if(%in: tensor<10xf32>) -> tensor<10xf32> { + %empty = tensor.empty() : tensor<10xf32> + %out = linalg.generic { + indexing_maps = [affine_map<(i) -> (i)>, affine_map<(i) -> (i)>], + iterator_types = ["parallel"]} + ins(%in : tensor<10xf32>) + outs(%empty : tensor<10xf32>) { + ^bb0(%a: f32, %b: f32): + %c42f = arith.constant 42.0 : f32 + %i = linalg.index 0 : index + %ret = affine.if #set(%i) -> f32 { + affine.yield %a : f32 + } else { + affine.yield %c42f : f32 + } + linalg.yield %ret : f32 + } -> tensor<10xf32> + return %out : tensor<10xf32> +} diff --git a/mlir/test/Dialect/Linalg/convert-conv2d-to-img2col.mlir b/mlir/test/Dialect/Linalg/convert-conv2d-to-img2col.mlir index c17f20b2d03ab..c7c846d7ecc9c 100644 --- a/mlir/test/Dialect/Linalg/convert-conv2d-to-img2col.mlir +++ b/mlir/test/Dialect/Linalg/convert-conv2d-to-img2col.mlir @@ -40,9 +40,9 @@ module attributes {transform.with_named_sequence} { // CHECK: %[[KINDEX:.+]] = linalg.index 2 : index // Compute input channel/convolved indices. -// CHECK: %[[ICINDEX:.+]] = affine.apply affine_map<()[s0] -> (s0 mod 4)>()[%[[KINDEX]]] -// CHECK: %[[CONVH:.+]] = affine.apply affine_map<()[s0, s1] -> (s0 floordiv 14 + s1 floordiv 12)>()[%[[MINDEX]], %[[KINDEX]]] -// CHECK: %[[CONVW:.+]] = affine.apply affine_map<()[s0, s1] -> (s0 mod 14 + (s1 mod 12) floordiv 4)>()[%[[MINDEX]], %[[KINDEX]]] +// CHECK: %[[ICINDEX:.+]] = affine.apply affine_map<(d0) -> (d0 mod 4)>(%[[KINDEX]]) +// CHECK: %[[CONVH:.+]] = affine.apply affine_map<(d0, d1) -> (d0 floordiv 14 + d1 floordiv 12)>(%[[MINDEX]], %[[KINDEX]]) +// CHECK: %[[CONVW:.+]] = affine.apply affine_map<(d0, d1) -> (d0 mod 14 + (d1 mod 12) floordiv 4)>(%[[MINDEX]], %[[KINDEX]]) // Extract from the input tensor. // CHECK: %[[EXTRACTED_INPUT:.+]] = tensor.extract @@ -227,9 +227,9 @@ module attributes {transform.with_named_sequence} { // CHECK-DAG: #[[MAP:.+]] = affine_map<(d0, d1, d2) -> (d0, d1, d2)> // Im2col maps -// CHECK-DAG: #[[MAP1:.+]] = affine_map<()[s0] -> (s0 floordiv 9)> -// CHECK-DAG: #[[MAP7:.+]] = affine_map<()[s0, s1] -> (s0 floordiv 14 + (s1 mod 9) floordiv 3)> -// CHECK-DAG: #[[MAP8:.+]] = affine_map<()[s0, s1] -> (s0 + s1 - (s0 floordiv 14) * 14 - (s1 floordiv 3) * 3)> +// CHECK-DAG: #[[MAP1:.+]] = affine_map<(d0) -> (d0 floordiv 9)> +// CHECK-DAG: #[[MAP7:.+]] = affine_map<(d0, d1) -> (d0 floordiv 14 + (d1 mod 9) floordiv 3)> +// CHECK-DAG: #[[MAP8:.+]] = affine_map<(d0, d1) -> (d0 + d1 - (d0 floordiv 14) * 14 - (d1 floordiv 3) * 3)> // CHECK-DAG: #[[LHSMAP:.+]] = affine_map<(d0, d1, d2, d3) -> (d1, d3)> @@ -251,9 +251,9 @@ module attributes {transform.with_named_sequence} { // CHECK: %[[NINDEX:.+]] = linalg.index 2 : index // Compute input channel/convolved indices. -// CHECK: %[[ICINDEX:.+]] = affine.apply #[[MAP1]]()[%[[KINDEX]]] -// CHECK: %[[CONVH:.+]] = affine.apply #[[MAP7]]()[%[[NINDEX]], %[[KINDEX]]] -// CHECK: %[[CONVW:.+]] = affine.apply #[[MAP8]]()[%[[NINDEX]], %[[KINDEX]]] +// CHECK: %[[ICINDEX:.+]] = affine.apply #[[MAP1]](%[[KINDEX]]) +// CHECK: %[[CONVH:.+]] = affine.apply #[[MAP7]](%[[NINDEX]], %[[KINDEX]]) +// CHECK: %[[CONVW:.+]] = affine.apply #[[MAP8]](%[[NINDEX]], %[[KINDEX]]) // Extract from the input tensor. // CHECK: %[[EXTRACTED_INPUT:.+]] = tensor.extract @@ -300,9 +300,9 @@ module attributes {transform.with_named_sequence} { // CHECK: %[[KINDEX:.+]] = linalg.index 2 : index // Compute input channel/convolved indices. -// CHECK: %[[ICINDEX:.+]] = affine.apply affine_map<()[s0] -> (s0 mod 4)>()[%[[KINDEX]]] -// CHECK: %[[CONVH:.+]] = affine.apply affine_map<()[s0, s1] -> (s0 floordiv 14 + s1 floordiv 12)>()[%[[MINDEX]], %[[KINDEX]]] -// CHECK: %[[CONVW:.+]] = affine.apply affine_map<()[s0, s1] -> (s0 mod 14 + (s1 mod 12) floordiv 4)>()[%[[MINDEX]], %[[KINDEX]]] +// CHECK: %[[ICINDEX:.+]] = affine.apply affine_map<(d0) -> (d0 mod 4)>(%[[KINDEX]]) +// CHECK: %[[CONVH:.+]] = affine.apply affine_map<(d0, d1) -> (d0 floordiv 14 + d1 floordiv 12)>(%[[MINDEX]], %[[KINDEX]]) +// CHECK: %[[CONVW:.+]] = affine.apply affine_map<(d0, d1) -> (d0 mod 14 + (d1 mod 12) floordiv 4)>(%[[MINDEX]], %[[KINDEX]]) // Extract from the input tensor. // CHECK: %[[EXTRACTED_INPUT:.+]] = tensor.extract diff --git a/mlir/test/Dialect/Linalg/fusion-elementwise-ops.mlir b/mlir/test/Dialect/Linalg/fusion-elementwise-ops.mlir index 613c23f35f6b1..a0405d9450edd 100644 --- a/mlir/test/Dialect/Linalg/fusion-elementwise-ops.mlir +++ b/mlir/test/Dialect/Linalg/fusion-elementwise-ops.mlir @@ -986,13 +986,13 @@ module { #map3 = affine_map<(d0, d1) -> (d0, d1)> // CHECK-DAG: [[$MAP0:#[a-zA-Z0-9_]*]] = affine_map<(d0, d1) -> (d0, d1)> -// CHECK-DAG: [[$MAP1:#[a-zA-Z0-9_]*]] = affine_map<()[s0] -> (s0 floordiv 4)> +// CHECK-DAG: [[$MAP1:#[a-zA-Z0-9_]*]] = affine_map<(d0) -> (d0 floordiv 4)> func.func @fuse_and_collapse(%arg0: tensor<3x4xindex>) -> tensor<2x12xindex> { %1 = tensor.empty() : tensor<2x3x4xindex> // CHECK: linalg.generic { // CHECK: %[[INDEX1:[a-zA-Z0-9_]+]] = linalg.index 1 : index - // CHECK-NEXT: %[[MAP:[a-zA-Z0-9_]+]] = affine.apply #map1()[%[[INDEX1]]] + // CHECK-NEXT: %[[MAP:[a-zA-Z0-9_]+]] = affine.apply #map1(%[[INDEX1]]) // CHECK-NEXT: linalg.yield %[[MAP]] : index %2 = linalg.generic {indexing_maps = [#map, #map1], iterator_types = ["parallel", "parallel", "parallel"]} ins(%arg0: tensor<3x4xindex>) outs(%1 : tensor<2x3x4xindex>) { ^bb0(%in: index, %out: index): diff --git a/mlir/test/Dialect/Linalg/tile-indexed.mlir b/mlir/test/Dialect/Linalg/tile-indexed.mlir index d96a251b01ccb..b4aa0a33bc592 100644 --- a/mlir/test/Dialect/Linalg/tile-indexed.mlir +++ b/mlir/test/Dialect/Linalg/tile-indexed.mlir @@ -19,13 +19,13 @@ module attributes {transform.with_named_sequence} { } } -// TILE-10n25-DAG: [[$MAP:#[a-zA-Z0-9_]*]] = affine_map<(d0)[s0] -> (d0 + s0)> +// TILE-10n25-DAG: [[$MAP:#[a-zA-Z0-9_]*]] = affine_map<(d0, d1) -> (d0 + d1)> // TILE-10n25-LABEL: func @indexed_vector // TILE-10n25: %[[C10:.*]] = arith.constant 10 : index // TILE-10n25: scf.for %[[J:.*]] = {{.*}} step %[[C10]] // TILE-10n25: linalg.generic // TILE-10n25: %[[I:.*]] = linalg.index 0 : index -// TILE-10n25: %[[NEW_I:.*]] = affine.apply [[$MAP]](%[[J]])[%[[I]]] +// TILE-10n25: %[[NEW_I:.*]] = affine.apply [[$MAP]](%[[I]], %[[J]]) // TILE-10n25: linalg.yield %[[NEW_I]] : index // ----- @@ -51,7 +51,7 @@ module attributes {transform.with_named_sequence} { } } -// TILE-10n25-DAG: [[$MAP:#[a-zA-Z0-9_]*]] = affine_map<(d0)[s0] -> (d0 + s0)> +// TILE-10n25-DAG: [[$MAP:#[a-zA-Z0-9_]*]] = affine_map<(d0, d1) -> (d0 + d1)> // TILE-10n25-LABEL: func @indexed_matrix // TILE-10n25-DAG: %[[C25:.*]] = arith.constant 25 : index // TILE-10n25-DAG: %[[C10:.*]] = arith.constant 10 : index @@ -59,8 +59,8 @@ module attributes {transform.with_named_sequence} { // TILE-10n25: scf.for %[[L:.*]] = {{.*}} step %[[C25]] // TILE-10n25: linalg.generic // TILE-10n25: %[[I:.*]] = linalg.index 0 : index -// TILE-10n25: %[[NEW_I:.*]] = affine.apply [[$MAP]](%[[K]])[%[[I]]] +// TILE-10n25: %[[NEW_I:.*]] = affine.apply [[$MAP]](%[[I]], %[[K]]) // TILE-10n25: %[[J:.*]] = linalg.index 1 : index -// TILE-10n25: %[[NEW_J:.*]] = affine.apply [[$MAP]](%[[L]])[%[[J]]] +// TILE-10n25: %[[NEW_J:.*]] = affine.apply [[$MAP]](%[[J]], %[[L]]) // TILE-10n25: %[[SUM:.*]] = arith.addi %[[NEW_I]], %[[NEW_J]] : index // TILE-10n25: linalg.yield %[[SUM]] : index diff --git a/mlir/test/Dialect/Linalg/transform-op-split.mlir b/mlir/test/Dialect/Linalg/transform-op-split.mlir index 7f0ef401c8422..68c849385ba6b 100644 --- a/mlir/test/Dialect/Linalg/transform-op-split.mlir +++ b/mlir/test/Dialect/Linalg/transform-op-split.mlir @@ -10,7 +10,7 @@ module attributes {transform.with_named_sequence} { func.func private @elem(%arg0: f32, %arg1: index, %arg2: index) -> f32 -// CHECK: #[[$ADD_42_MAP:.+]] = affine_map<()[s0] -> (s0 + 42)> +// CHECK: #[[$ADD_42_MAP:.+]] = affine_map<(d0) -> (d0 + 42)> // CHECK-LABEL: @one_d_static // CHECK-SAME: %[[IN:.+]]: tensor<100xf32>, %[[OUT:.+]]: tensor<100xf32> @@ -30,7 +30,7 @@ func.func @one_d_static(%arg0: tensor<100xf32>, %arg1: tensor<100xf32>) -> tenso // CHECK: ins(%[[IN_SLICE_HIGH]] // CHECK: outs(%[[OUT_SLICE_HIGH]] // CHECK: %[[IDX:.+]] = linalg.index 0 - // CHECK: affine.apply #[[$ADD_42_MAP]]()[%[[IDX]]] + // CHECK: affine.apply #[[$ADD_42_MAP]](%[[IDX]]) // CHECK: func.call @elem // CHECK: %[[RES:.+]] = tensor.insert_slice %[[RES_SLICE_HIGH]] into %[[RES_PARTIAL]][42] [58] [1] %0 = linalg.generic { diff --git a/mlir/test/Interfaces/TilingInterface/tile-using-interface.mlir b/mlir/test/Interfaces/TilingInterface/tile-using-interface.mlir index 2d9d7e432d875..8eb1311170c66 100644 --- a/mlir/test/Interfaces/TilingInterface/tile-using-interface.mlir +++ b/mlir/test/Interfaces/TilingInterface/tile-using-interface.mlir @@ -259,14 +259,14 @@ module attributes {transform.with_named_sequence} { transform.yield } } -// CHECK: #[[$MAP_ADD:.+]] = affine_map<(d0)[s0] -> (d0 + s0)> +// CHECK: #[[$MAP_ADD:.+]] = affine_map<(d0, d1) -> (d0 + d1)> // CHECK-LABEL: @indexed_semantics // CHECK: scf.for %[[I0:.+]] = %{{.*}} to %{{.*}} step %{{.*}} // CHECK: scf.for %[[I1:.+]] = %{{.*}} to %{{.*}} step %{{.*}} // CHECK: %[[INDEX0:.+]] = linalg.index 0 -// CHECK: %[[INDEX0_AMENDED:.+]] = affine.apply #[[$MAP_ADD]](%[[I0]])[%[[INDEX0]]] +// CHECK: %[[INDEX0_AMENDED:.+]] = affine.apply #[[$MAP_ADD]](%[[INDEX0]], %[[I0]]) // CHECK: %[[INDEX1:.+]] = linalg.index 1 -// CHECK: %[[INDEX1_AMENDED:.+]] = affine.apply #[[$MAP_ADD]](%[[I1]])[%[[INDEX1]]] +// CHECK: %[[INDEX1_AMENDED:.+]] = affine.apply #[[$MAP_ADD]](%[[INDEX1]], %[[I1]]) // CHECK: arith.addi %[[INDEX0_AMENDED]], %[[INDEX1_AMENDED]] // ----- diff --git a/mlir/test/Interfaces/TilingInterface/tile-using-scfforall.mlir b/mlir/test/Interfaces/TilingInterface/tile-using-scfforall.mlir index 745a82fc0da75..53dd0c6a2425c 100644 --- a/mlir/test/Interfaces/TilingInterface/tile-using-scfforall.mlir +++ b/mlir/test/Interfaces/TilingInterface/tile-using-scfforall.mlir @@ -205,7 +205,7 @@ module attributes {transform.with_named_sequence} { // ----- -// CHECK: #[[$MAP_ADD:.+]] = affine_map<(d0)[s0] -> (d0 + s0)> +// CHECK: #[[$MAP_ADD:.+]] = affine_map<(d0, d1) -> (d0 + d1)> func.func @indexed_semantics(%arg0: tensor, %arg1: tensor) -> tensor { // Check that we correctly amend "linalg.index" results. @@ -241,9 +241,9 @@ module attributes {transform.with_named_sequence} { // CHECK-LABEL: @indexed_semantics // CHECK: scf.forall (%[[I0:.+]], %[[I1:.+]]) = // CHECK: %[[INDEX0:.+]] = linalg.index 0 -// CHECK: %[[INDEX0_AMENDED:.+]] = affine.apply #[[$MAP_ADD]](%[[I0]])[%[[INDEX0]]] +// CHECK: %[[INDEX0_AMENDED:.+]] = affine.apply #[[$MAP_ADD]](%[[INDEX0]], %[[I0]]) // CHECK: %[[INDEX1:.+]] = linalg.index 1 -// CHECK: %[[INDEX1_AMENDED:.+]] = affine.apply #[[$MAP_ADD]](%[[I1]])[%[[INDEX1]]] +// CHECK: %[[INDEX1_AMENDED:.+]] = affine.apply #[[$MAP_ADD]](%[[INDEX1]], %[[I1]]) // CHECK: arith.addi %[[INDEX0_AMENDED]], %[[INDEX1_AMENDED]] // -----