<feed xmlns='http://www.w3.org/2005/Atom'>
<title>llvm-project.git/mlir/lib/Dialect/MemRef/Transforms/RuntimeOpVerification.cpp, branch main</title>
<subtitle>Unnamed repository; edit this file 'description' to name the repository.
</subtitle>
<link rel='alternate' type='text/html' href='https://git.belthelziquor.com/llvm-project.git/'/>
<entry>
<title>[mlir][memref] Fix runtime verification for memref.subview for empty memref subviews  (#166581)</title>
<updated>2025-11-11T23:36:41+00:00</updated>
<author>
<name>Hanumanth</name>
<email>hhanuman@mathworks.com</email>
</author>
<published>2025-11-11T23:36:41+00:00</published>
<link rel='alternate' type='text/html' href='https://git.belthelziquor.com/llvm-project.git/commit/?id=a664f584f9596bf61aa9be35967dc578e58f6ca3'/>
<id>a664f584f9596bf61aa9be35967dc578e58f6ca3</id>
<content type='text'>
This PR applies the same fix from #166569 to `memref.subview`. That PR
fixed the issue for `tensor.extract_slice`, and this one addresses the
identical problem for `memref.subview`.

The runtime verification for `memref.subview` incorrectly rejects valid
empty subviews (size=0) starting at the memref boundary.

**Example that demonstrates the issue:**

```mlir
func.func @subview_with_empty_slice(%memref: memref&lt;10x4x1xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt;, 
                                     %dim_0: index, 
                                     %dim_1: index, 
                                     %dim_2: index,
                                     %offset: index) {
    // When called with: offset=10, dim_0=0, dim_1=4, dim_2=1
    // Runtime verification fails: "offset 0 is out-of-bounds"
    %subview = memref.subview %memref[%offset, 0, 0] [%dim_0, %dim_1, %dim_2] [1, 1, 1] :
        memref&lt;10x4x1xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt; to
        memref&lt;?x?x?xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt;
    return
}
```

When `%offset=10` and `%dim_0=0`, we're creating an empty subview (zero
elements along dimension 0) starting at the boundary. The current
verification enforces `offset &lt; dim_size`, which evaluates to `10 &lt; 10`
and fails. I feel this should be valid since no memory is accessed.

**The fix:**

Same as #166569 - make the offset check conditional on subview size:
- Empty subview (size == 0): allow `0 &lt;= offset &lt;= dim_size`
- Non-empty subview (size &gt; 0): require `0 &lt;= offset &lt; dim_size`

Please see #166569 for motivation and rationale.

---

Co-authored-by: Hanumanth Hanumantharayappa &lt;hhanuman@ah-hhanuman-l.dhcp.mathworks.com&gt;</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
This PR applies the same fix from #166569 to `memref.subview`. That PR
fixed the issue for `tensor.extract_slice`, and this one addresses the
identical problem for `memref.subview`.

The runtime verification for `memref.subview` incorrectly rejects valid
empty subviews (size=0) starting at the memref boundary.

**Example that demonstrates the issue:**

```mlir
func.func @subview_with_empty_slice(%memref: memref&lt;10x4x1xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt;, 
                                     %dim_0: index, 
                                     %dim_1: index, 
                                     %dim_2: index,
                                     %offset: index) {
    // When called with: offset=10, dim_0=0, dim_1=4, dim_2=1
    // Runtime verification fails: "offset 0 is out-of-bounds"
    %subview = memref.subview %memref[%offset, 0, 0] [%dim_0, %dim_1, %dim_2] [1, 1, 1] :
        memref&lt;10x4x1xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt; to
        memref&lt;?x?x?xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt;
    return
}
```

When `%offset=10` and `%dim_0=0`, we're creating an empty subview (zero
elements along dimension 0) starting at the boundary. The current
verification enforces `offset &lt; dim_size`, which evaluates to `10 &lt; 10`
and fails. I feel this should be valid since no memory is accessed.

**The fix:**

Same as #166569 - make the offset check conditional on subview size:
- Empty subview (size == 0): allow `0 &lt;= offset &lt;= dim_size`
- Non-empty subview (size &gt; 0): require `0 &lt;= offset &lt; dim_size`

Please see #166569 for motivation and rationale.

---

Co-authored-by: Hanumanth Hanumantharayappa &lt;hhanuman@ah-hhanuman-l.dhcp.mathworks.com&gt;</pre>
</div>
</content>
</entry>
<entry>
<title>[mlir][memref] Fix runtime verification for memref.subview when size dimension value is 0 (#164897)</title>
<updated>2025-10-27T18:43:45+00:00</updated>
<author>
<name>Hanumanth</name>
<email>hhanuman@mathworks.com</email>
</author>
<published>2025-10-27T18:43:45+00:00</published>
<link rel='alternate' type='text/html' href='https://git.belthelziquor.com/llvm-project.git/commit/?id=cbe7c49e93b630d3388dba2663b08a3c5c1bc8b6'/>
<id>cbe7c49e93b630d3388dba2663b08a3c5c1bc8b6</id>
<content type='text'>
Previously, the runtime verification pass would insert assertion
statements with conditions that always evaluate to false for
semantically valid `memref.subview` operations where one of the
dimensions had a size of 0.

The `memref.subview` runtime verification logic was unconditionally
generating checks for the position of the last element (`offset + (size
- 1) * stride`). When `size` is 0, this causes the assertion condition
to always be false, leading to runtime failures even though the
operation is semantically valid.

This patch fixes the issue by making the `lastPos` check conditional.
The offset is always verified, but the endpoint check is only performed
when `size &gt; 0` to avoid generating spurious assert statements.

This issue was discovered through a LiteRT model, where a dynamic shape
calculation resulted in a zero-sized dimension being passed to
`memref.subview`. The following is a simplified IR snippet from the
model. After running the runtime verification pass, an assertion that
always fails is generated because the SSA value `%5` becomes 0.

```mlir
module {
  memref.global "private" constant @__constant_2xi32 : memref&lt;2xi32&gt; = dense&lt;-1&gt; {alignment = 64 : i64}
  memref.global "private" constant @__constant_1xi32 : memref&lt;1xi32&gt; = dense&lt;0&gt; {alignment = 64 : i64}
  func.func @simpleRepro(%arg0: memref&lt;10x4x1xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt;) -&gt; memref&lt;?x?x?xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt; {
    %c2 = arith.constant 2 : index
    %c4 = arith.constant 4 : index
    %c1 = arith.constant 1 : index
    %c10 = arith.constant 10 : index
    %c0 = arith.constant 0 : index
    %c-1 = arith.constant -1 : index
    %0 = memref.get_global @__constant_1xi32 : memref&lt;1xi32&gt;
    %1 = memref.get_global @__constant_2xi32 : memref&lt;2xi32&gt;
    %alloca = memref.alloca() {alignment = 64 : i64} : memref&lt;3xi32&gt;
    %subview = memref.subview %alloca[0] [1] [1] : memref&lt;3xi32&gt; to memref&lt;1xi32, strided&lt;[1]&gt;&gt;
    memref.copy %0, %subview : memref&lt;1xi32&gt; to memref&lt;1xi32, strided&lt;[1]&gt;&gt;
    %subview_0 = memref.subview %alloca[1] [2] [1] : memref&lt;3xi32&gt; to memref&lt;2xi32, strided&lt;[1], offset: 1&gt;&gt;
    memref.copy %1, %subview_0 : memref&lt;2xi32&gt; to memref&lt;2xi32, strided&lt;[1], offset: 1&gt;&gt;
    %2 = memref.load %alloca[%c0] : memref&lt;3xi32&gt;
    %3 = index.casts %2 : i32 to index
    %4 = arith.cmpi eq, %3, %c-1 : index
    %5 = arith.select %4, %c10, %3 : index
    %6 = memref.load %alloca[%c1] : memref&lt;3xi32&gt;
    %7 = index.casts %6 : i32 to index
    %8 = arith.cmpi eq, %7, %c-1 : index
    %9 = arith.select %8, %c4, %7 : index
    %10 = memref.load %alloca[%c2] : memref&lt;3xi32&gt;
    %11 = index.casts %10 : i32 to index
    %12 = arith.cmpi eq, %11, %c-1 : index
    %13 = arith.select %12, %c1, %11 : index
    %subview_1 = memref.subview %arg0[0, 0, 0] [%5, %9, %13] [1, 1, 1] : memref&lt;10x4x1xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt; to memref&lt;?x?x?xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt;
    return %subview_1 : memref&lt;?x?x?xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt;
  }
}
```

P.S. This is a similar issue to the one fixed for `tensor.extract_slice`
in https://github.com/llvm/llvm-project/pull/164878

---------

Co-authored-by: Hanumanth Hanumantharayappa &lt;hhanuman@ah-hhanuman-l.dhcp.mathworks.com&gt;</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
Previously, the runtime verification pass would insert assertion
statements with conditions that always evaluate to false for
semantically valid `memref.subview` operations where one of the
dimensions had a size of 0.

The `memref.subview` runtime verification logic was unconditionally
generating checks for the position of the last element (`offset + (size
- 1) * stride`). When `size` is 0, this causes the assertion condition
to always be false, leading to runtime failures even though the
operation is semantically valid.

This patch fixes the issue by making the `lastPos` check conditional.
The offset is always verified, but the endpoint check is only performed
when `size &gt; 0` to avoid generating spurious assert statements.

This issue was discovered through a LiteRT model, where a dynamic shape
calculation resulted in a zero-sized dimension being passed to
`memref.subview`. The following is a simplified IR snippet from the
model. After running the runtime verification pass, an assertion that
always fails is generated because the SSA value `%5` becomes 0.

```mlir
module {
  memref.global "private" constant @__constant_2xi32 : memref&lt;2xi32&gt; = dense&lt;-1&gt; {alignment = 64 : i64}
  memref.global "private" constant @__constant_1xi32 : memref&lt;1xi32&gt; = dense&lt;0&gt; {alignment = 64 : i64}
  func.func @simpleRepro(%arg0: memref&lt;10x4x1xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt;) -&gt; memref&lt;?x?x?xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt; {
    %c2 = arith.constant 2 : index
    %c4 = arith.constant 4 : index
    %c1 = arith.constant 1 : index
    %c10 = arith.constant 10 : index
    %c0 = arith.constant 0 : index
    %c-1 = arith.constant -1 : index
    %0 = memref.get_global @__constant_1xi32 : memref&lt;1xi32&gt;
    %1 = memref.get_global @__constant_2xi32 : memref&lt;2xi32&gt;
    %alloca = memref.alloca() {alignment = 64 : i64} : memref&lt;3xi32&gt;
    %subview = memref.subview %alloca[0] [1] [1] : memref&lt;3xi32&gt; to memref&lt;1xi32, strided&lt;[1]&gt;&gt;
    memref.copy %0, %subview : memref&lt;1xi32&gt; to memref&lt;1xi32, strided&lt;[1]&gt;&gt;
    %subview_0 = memref.subview %alloca[1] [2] [1] : memref&lt;3xi32&gt; to memref&lt;2xi32, strided&lt;[1], offset: 1&gt;&gt;
    memref.copy %1, %subview_0 : memref&lt;2xi32&gt; to memref&lt;2xi32, strided&lt;[1], offset: 1&gt;&gt;
    %2 = memref.load %alloca[%c0] : memref&lt;3xi32&gt;
    %3 = index.casts %2 : i32 to index
    %4 = arith.cmpi eq, %3, %c-1 : index
    %5 = arith.select %4, %c10, %3 : index
    %6 = memref.load %alloca[%c1] : memref&lt;3xi32&gt;
    %7 = index.casts %6 : i32 to index
    %8 = arith.cmpi eq, %7, %c-1 : index
    %9 = arith.select %8, %c4, %7 : index
    %10 = memref.load %alloca[%c2] : memref&lt;3xi32&gt;
    %11 = index.casts %10 : i32 to index
    %12 = arith.cmpi eq, %11, %c-1 : index
    %13 = arith.select %12, %c1, %11 : index
    %subview_1 = memref.subview %arg0[0, 0, 0] [%5, %9, %13] [1, 1, 1] : memref&lt;10x4x1xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt; to memref&lt;?x?x?xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt;
    return %subview_1 : memref&lt;?x?x?xf32, strided&lt;[?, ?, ?], offset: ?&gt;&gt;
  }
}
```

P.S. This is a similar issue to the one fixed for `tensor.extract_slice`
in https://github.com/llvm/llvm-project/pull/164878

---------

Co-authored-by: Hanumanth Hanumantharayappa &lt;hhanuman@ah-hhanuman-l.dhcp.mathworks.com&gt;</pre>
</div>
</content>
</entry>
<entry>
<title>[MLIR] Reuse AsmState to enable fast generate-runtime-verification pass; add location-only pass option (#160331)</title>
<updated>2025-10-08T10:48:34+00:00</updated>
<author>
<name>Hanchenng Wu</name>
<email>42194432+HanchengWu@users.noreply.github.com</email>
</author>
<published>2025-10-08T10:48:34+00:00</published>
<link rel='alternate' type='text/html' href='https://git.belthelziquor.com/llvm-project.git/commit/?id=a6d1a52b8da9cb3c351a086180f8b871f0fd2a6e'/>
<id>a6d1a52b8da9cb3c351a086180f8b871f0fd2a6e</id>
<content type='text'>
The pass generate-runtime-verification generates additional runtime op
verification checks.

Currently, the pass is extremely expensive. For example, with a
mobilenet v2 ssd network(converted to mlir), running this pass alone in
debug mode will take 30 minutes. The same observation has been made to
other networks as small as 5 Mb.

The culprit is this line "op-&gt;print(stream, flags);" in function
"RuntimeVerifiableOpInterface::generateErrorMessage" in File
mlir/lib/Interfaces/RuntimeVerifiableOpInterface.cpp.

As we are printing the op with all the names of the operands in the
middle end, we are constructing a new SSANameState for each
op-&gt;print(...) call. Thus, we are doing a new SSA analysis for each
error message printed.

Perf profiling shows that 98% percent of the time is spent in the
constructor of SSANameState.

This change refactored the message generator. We use a toplevel
AsmState, and reuse it with all the op-print(stream, asmState). With a
release build, this change reduces the pass exeuction time from ~160
seconds to 0.3 seconds on my machine.

This change also adds verbose options to generate-runtime-verification
pass.
verbose 0: print only source location with error message.
verbose 1: print the full op, including the name of the operands.</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
The pass generate-runtime-verification generates additional runtime op
verification checks.

Currently, the pass is extremely expensive. For example, with a
mobilenet v2 ssd network(converted to mlir), running this pass alone in
debug mode will take 30 minutes. The same observation has been made to
other networks as small as 5 Mb.

The culprit is this line "op-&gt;print(stream, flags);" in function
"RuntimeVerifiableOpInterface::generateErrorMessage" in File
mlir/lib/Interfaces/RuntimeVerifiableOpInterface.cpp.

As we are printing the op with all the names of the operands in the
middle end, we are constructing a new SSANameState for each
op-&gt;print(...) call. Thus, we are doing a new SSA analysis for each
error message printed.

Perf profiling shows that 98% percent of the time is spent in the
constructor of SSANameState.

This change refactored the message generator. We use a toplevel
AsmState, and reuse it with all the op-print(stream, asmState). With a
release build, this change reduces the pass exeuction time from ~160
seconds to 0.3 seconds on my machine.

This change also adds verbose options to generate-runtime-verification
pass.
verbose 0: print only source location with error message.
verbose 1: print the full op, including the name of the operands.</pre>
</div>
</content>
</entry>
<entry>
<title>[mlir][NFC] update `mlir/Dialect` create APIs (33/n) (#150659)</title>
<updated>2025-07-25T20:13:55+00:00</updated>
<author>
<name>Maksim Levental</name>
<email>maksim.levental@gmail.com</email>
</author>
<published>2025-07-25T20:13:55+00:00</published>
<link rel='alternate' type='text/html' href='https://git.belthelziquor.com/llvm-project.git/commit/?id=c090ed53fb73f59cf221f5610430af8047758117'/>
<id>c090ed53fb73f59cf221f5610430af8047758117</id>
<content type='text'>
See https://github.com/llvm/llvm-project/pull/147168 for more info.</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
See https://github.com/llvm/llvm-project/pull/147168 for more info.</pre>
</div>
</content>
</entry>
<entry>
<title>[mlir][NFC] update `mlir/Dialect` create APIs (18/n) (#149925)</title>
<updated>2025-07-24T20:38:30+00:00</updated>
<author>
<name>Maksim Levental</name>
<email>maksim.levental@gmail.com</email>
</author>
<published>2025-07-24T20:38:30+00:00</published>
<link rel='alternate' type='text/html' href='https://git.belthelziquor.com/llvm-project.git/commit/?id=a636b7bfdd1d8304b78e8b42ec900a21736d4afb'/>
<id>a636b7bfdd1d8304b78e8b42ec900a21736d4afb</id>
<content type='text'>
See https://github.com/llvm/llvm-project/pull/147168 for more info.</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
See https://github.com/llvm/llvm-project/pull/147168 for more info.</pre>
</div>
</content>
</entry>
<entry>
<title>[llvm] Remove unused includes (NFC) (#148342)</title>
<updated>2025-07-12T18:28:55+00:00</updated>
<author>
<name>Kazu Hirata</name>
<email>kazu@google.com</email>
</author>
<published>2025-07-12T18:28:55+00:00</published>
<link rel='alternate' type='text/html' href='https://git.belthelziquor.com/llvm-project.git/commit/?id=d5def016b6ee3dcf4e1848ba39aba07e80714b75'/>
<id>d5def016b6ee3dcf4e1848ba39aba07e80714b75</id>
<content type='text'>
These are identified by misc-include-cleaner.  I've filtered out those
that break builds.  Also, I'm staying away from llvm-config.h,
config.h, and Compiler.h, which likely cause platform- or
compiler-specific build failures.</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
These are identified by misc-include-cleaner.  I've filtered out those
that break builds.  Also, I'm staying away from llvm-config.h,
config.h, and Compiler.h, which likely cause platform- or
compiler-specific build failures.</pre>
</div>
</content>
</entry>
<entry>
<title>[mlir][memref] Remove runtime verification for `memref.reinterpret_cast` (#132547)</title>
<updated>2025-05-06T07:40:28+00:00</updated>
<author>
<name>Matthias Springer</name>
<email>me@m-sp.org</email>
</author>
<published>2025-05-06T07:40:28+00:00</published>
<link rel='alternate' type='text/html' href='https://git.belthelziquor.com/llvm-project.git/commit/?id=fd161cf56f4356c38f82a6d68a80236e00bce39d'/>
<id>fd161cf56f4356c38f82a6d68a80236e00bce39d</id>
<content type='text'>
The runtime verification code used to verify that the result of a
`memref.reinterpret_cast` is in-bounds with respect to the source
memref. This is incorrect: `memref.reinterpret_cast` allows users to
construct almost arbitrary memref descriptors and there is no
correctness expectation.

This op is supposed to be used when the user "knows what they are
doing." Similarly, the static verifier of `memref.reinterpret_cast` does
not verify in-bounds semantics either.
</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
The runtime verification code used to verify that the result of a
`memref.reinterpret_cast` is in-bounds with respect to the source
memref. This is incorrect: `memref.reinterpret_cast` allows users to
construct almost arbitrary memref descriptors and there is no
correctness expectation.

This op is supposed to be used when the user "knows what they are
doing." Similarly, the static verifier of `memref.reinterpret_cast` does
not verify in-bounds semantics either.
</pre>
</div>
</content>
</entry>
<entry>
<title>[mlir][memref] Add runtime verification for `memref.atomic_rmw` (#130414)</title>
<updated>2025-04-30T11:45:11+00:00</updated>
<author>
<name>Matthias Springer</name>
<email>me@m-sp.org</email>
</author>
<published>2025-04-30T11:45:11+00:00</published>
<link rel='alternate' type='text/html' href='https://git.belthelziquor.com/llvm-project.git/commit/?id=120e940356561035bf37bc4fcb6fab771e7a9b7d'/>
<id>120e940356561035bf37bc4fcb6fab771e7a9b7d</id>
<content type='text'>
Implement runtime verification for `memref.atomic_rmw` and
`memref.generic_atomic_rmw`. Also add a missing test for `memref.store`.</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
Implement runtime verification for `memref.atomic_rmw` and
`memref.generic_atomic_rmw`. Also add a missing test for `memref.store`.</pre>
</div>
</content>
</entry>
<entry>
<title>[mlir][memref] Fix build after #132545 (#133760)</title>
<updated>2025-03-31T17:38:55+00:00</updated>
<author>
<name>Matthias Springer</name>
<email>me@m-sp.org</email>
</author>
<published>2025-03-31T17:38:55+00:00</published>
<link rel='alternate' type='text/html' href='https://git.belthelziquor.com/llvm-project.git/commit/?id=bc3b1b06c6e59a0de5b4b3607816a9255ca01df9'/>
<id>bc3b1b06c6e59a0de5b4b3607816a9255ca01df9</id>
<content type='text'>
There was a typo in the error message.</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
There was a typo in the error message.</pre>
</div>
</content>
</entry>
<entry>
<title>[mlir][memref] Improve runtime verification for `memref.subview` (#132545)</title>
<updated>2025-03-31T17:24:30+00:00</updated>
<author>
<name>Matthias Springer</name>
<email>me@m-sp.org</email>
</author>
<published>2025-03-31T17:24:30+00:00</published>
<link rel='alternate' type='text/html' href='https://git.belthelziquor.com/llvm-project.git/commit/?id=8b06da16827829c9b142f591303d3c66aab926b9'/>
<id>8b06da16827829c9b142f591303d3c66aab926b9</id>
<content type='text'>
This commit addresses a TODO in the runtime verification of
`memref.subview`. Each dimension is now verified: the offset must be
in-bounds and the slice must not run out-of-bounds.

This commit aligns runtime verification with static op verification
(which was improved in #133086).</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
This commit addresses a TODO in the runtime verification of
`memref.subview`. Each dimension is now verified: the offset must be
in-bounds and the slice must not run out-of-bounds.

This commit aligns runtime verification with static op verification
(which was improved in #133086).</pre>
</div>
</content>
</entry>
</feed>
