<html>
<head>
<base href="https://bugs.llvm.org/">
</head>
<body><table border="1" cellspacing="0" cellpadding="8">
<tr>
<th>Bug ID</th>
<td><a class="bz_bug_link
bz_status_NEW "
title="NEW - SROA does not split alloca into more fine-graied allocas iff index into it is variable"
href="https://bugs.llvm.org/show_bug.cgi?id=51807">51807</a>
</td>
</tr>
<tr>
<th>Summary</th>
<td>SROA does not split alloca into more fine-graied allocas iff index into it is variable
</td>
</tr>
<tr>
<th>Product</th>
<td>libraries
</td>
</tr>
<tr>
<th>Version</th>
<td>trunk
</td>
</tr>
<tr>
<th>Hardware</th>
<td>PC
</td>
</tr>
<tr>
<th>OS</th>
<td>Linux
</td>
</tr>
<tr>
<th>Status</th>
<td>NEW
</td>
</tr>
<tr>
<th>Severity</th>
<td>enhancement
</td>
</tr>
<tr>
<th>Priority</th>
<td>P
</td>
</tr>
<tr>
<th>Component</th>
<td>Scalar Optimizations
</td>
</tr>
<tr>
<th>Assignee</th>
<td>unassignedbugs@nondot.org
</td>
</tr>
<tr>
<th>Reporter</th>
<td>lebedev.ri@gmail.com
</td>
</tr>
<tr>
<th>CC</th>
<td>llvm-bugs@lists.llvm.org
</td>
</tr></table>
<p>
<div>
<pre>Let's suppose we have the following:
```
struct Outer {
int pre[4];
int array[4];
int post[4];
};
int src(int value, int idx0, int idx1) {
Outer storage;
storage.array[idx0] = value;
return storage.array[idx1];
}
```
So only the `Outer::array` is only ever used.
You'd think we'd be able to chop up the `storage` allocation,
and only allocate the `array` itself.
Alive doesn't like that because iff idx1 is not in [0, 4),
we'll now have poison instead of reading from `Outer::post[0]`.
But it seems like alive2 doesn't complain iff we make the index in-bounds:
int tgt(int value, int idx0, int idx1) {
int array[4];
array[idx0] = value;
return array[idx1 & 3];
}
$ ./alive-tv /tmp/test.ll --smt-to=60000
----------------------------------------
define i32 @src(i32 %value, i32 %idx0, i32 %idx1) noread nowrite nofree
willreturn {
%entry:
%storage = alloca i64 48, align 4, dead
%0 = bitcast * %storage to *
start_lifetime * %0
%idxprom = sext i32 %idx0 to i64
%arrayidx = gep inbounds * %storage, 48 x i64 0, 1 x i64 16, 4 x i64 %idxprom
store i32 %value, * %arrayidx, align 4
%idxprom2 = sext i32 %idx1 to i64
%arrayidx3 = gep inbounds * %storage, 48 x i64 0, 1 x i64 16, 4 x i64
%idxprom2
%1 = load i32, * %arrayidx3, align 4
free * %0 unconstrained
ret i32 %1
}
=>
define i32 @tgt(i32 %value, i32 %idx0, i32 %idx1) noread nowrite nofree
willreturn {
%entry:
%array = alloca i64 16, align 16, dead
%0 = bitcast * %array to *
start_lifetime * %0
%idxprom = sext i32 %idx0 to i64
%arrayidx = gep inbounds * %array, 16 x i64 0, 4 x i64 %idxprom
store i32 %value, * %arrayidx, align 4
%and = and i32 %idx1, 3
%1 = zext i32 %and to i64
%arrayidx2 = gep inbounds * %array, 16 x i64 0, 4 x i64 %1
%2 = load i32, * %arrayidx2, align 4
free * %0 unconstrained
ret i32 %2
}
ERROR: Timeout
Can we do this, or is this also illegal?</pre>
</div>
</p>
<hr>
<span>You are receiving this mail because:</span>
<ul>
<li>You are on the CC list for the bug.</li>
</ul>
</body>
</html>