<table border="1" cellspacing="0" cellpadding="8">
<tr>
<th>Issue</th>
<td>
<a href=https://github.com/llvm/llvm-project/issues/234176>234176</a>
</td>
</tr>
<tr>
<th>Summary</th>
<td>
[SLPVectorizer] Crash in getStoreMinimumVF on stores of small literal struct types such as { i1, i16 }
</td>
</tr>
<tr>
<th>Labels</th>
<td>
new issue
</td>
</tr>
<tr>
<th>Assignees</th>
<td>
</td>
</tr>
<tr>
<th>Reporter</th>
<td>
vekazt
</td>
</tr>
</table>
<pre>
The SLP vectorizer crashes on two adjacent stores of a small literal struct value.
Reproducer (`opt -passes=slp-vectorizer`):
```llvm
target triple = "x86_64-unknown-linux-gnu"
define void @f(ptr %p, { i1, i16 } %x, { i1, i16 } %y) {
store { i1, i16 } %x, ptr %p, align 4
%q = getelementptr i8, ptr %p, i64 4
store { i1, i16 } %y, ptr %q, align 4
ret void
}
```
With assertions (trunk on Compiler Explorer, 2026-10-21):
```
opt: llvm/lib/IR/Type.cpp:845: static llvm::FixedVectorType* llvm::FixedVectorType::get(llvm::Type*, unsigned int): Assertion `isValidElementType(ElementType) && "Element type of a VectorType must " "be an integer, floating point, " "pointer type, or a valid target " "extension type."' failed.
Stack dump:
0. Program arguments: opt -S -passes=slp-vectorizer <source>
1. Running pass "function(slp-vectorizer)" on module "<source>"
2. Running pass "slp-vectorizer" on function "f"
#9 llvm::FixedVectorType::get(llvm::Type*, unsigned int)
#10 llvm::X86TTIImpl::getStoreMinimumVF(unsigned int, llvm::Type*, llvm::Type*, llvm::Align, unsigned int) const
#11 llvm::SLPVectorizerPass::vectorizeStores(llvm::ArrayRef<llvm::StoreInst*>, llvm::slpvectorizer::BoUpSLP&, llvm::DenseSet<...>&, bool)
#12 llvm::SLPVectorizerPass::vectorizeStoreChains(llvm::slpvectorizer::BoUpSLP&)::'lambda3'(...)
#13 llvm::SLPVectorizerPass::vectorizeStoreChains(llvm::slpvectorizer::BoUpSLP&)
#14 llvm::SLPVectorizerPass::runImpl(...)
#15 llvm::SLPVectorizerPass::run(llvm::Function&, llvm::AnalysisManager<llvm::Function>&)
```
Without assertions, opt crashes in `llvm::VectorType::get` on the same path. `clang -O3` crashes the same way on modules that contain such stores.
Versions:
- 22.1.0: no crash; the stores are left unchanged.
- 23.1.0, 23.1.3 (Arch Linux package) and trunk: crash.
Notes:
- With `-passes=slp-vectorizer` alone, structs of 4 bytes or less crash: `{ i1, i8 }`, `{ i1, i16 }`, `{ i8, i16 }`, `{ i16, i16 }`. Eight-byte structs such as `{ i1, i32 }` and `{ i32, i32 }` do not, presumably because the base `getStoreMinimumVF` only builds a vector type while `VF > 2`.
- In the full `-O3` pipeline, InstCombine first splits stores of padding-free structs such as `{ i1, i8 }` into per-field stores. Padded structs such as `{ i1, i16 }` stay whole and reach SLP, so they crash `clang -O3`.
- Likely cause (not bisected): #199433 (074b6beca94b) changed `isValidElementType` in SLPVectorizer.cpp from `VectorType::isValidElementType(Ty)` to `canVectorizeTy(Ty)`, which accepts unpacked literal structs of scalars. `collectSeedInstructions` uses `isValidElementType` to filter store seeds, so struct-typed stores now reach `vectorizeStores` and `getStoreMinimumVF`. The comment on `canVectorizeTy` in VectorTypeUtils.h says a vectorized struct can't be used for vectorizing loads/stores.
- Related: #221715 (struct-typed scalars in `canBuildSplitNode`). This reproducer still crashes on trunk.
</pre>
<img width="1" height="1" alt="" src="http://email.email.llvm.org/o/eJy8V9tP8zgW_2vcl6NWqdOmzUMfQqESEjOLgGH3beUkp40Hx87YDtDvr18du_evfOxKq5FAauxzv_4snJMbjbhg0xs2vR2I3jfGLt7xTfzwg9LU28VLg_D88AjvWHlj5Q-0UFnhGnRgNPgPA6L-U1SoPThvLB2vQYBrhVKgpEcrFDhv-8rDu1A9jlhSsKR4ws6auq_QAuNzliWm8zDshHPoWHrrVDc8qmRZwnjO0iLy0mf4U-q9ZUnhhd2gB29lpxBYeguM88959u9sMuz1mzYfeqik7j-HG90zzqOUGtdSI7wbWQObJGvG550na6Yd40tgsxuQY_olxxmwGQmdfn55s2U8pxuWFBAj8QsJp3qEkhsNk8DH-PSvYP8GPSpsUXsilfNLJplNdiy_ULU94frrUpVFH1ynWMxuT4Mao_NP6RugbFgvjXaUJG97_UZZX5q2kwot3H12yli0JJwnPBuOkyEfX00VSwrTeZYWEJLGV0qWjK_unxhfvWw7HFVdx9JiPpkSjfPCyyqSpgVLi5X8xPo1FARRM1784jIcbtAzPj8S7djI1F6Hsq9Bah-NhWLvKbAske5VKFnfxQxExvnZVw6MZ4xnVGi7C_DbDmPxH02BtneeiOi_RBCadOImhmytjPBSb6AzwZLlnjJ8ow0i6dhYENQ9soZdre8I8dOjdmQ2kY6otvkM1kIqrKnRnr2o3qDu2y5mJBmxJH-0ZmNFC8JuerLcUQBC-z1_2YHA0qUzva2QpXcsKcYk6KnXOpgvHBUIX_e6ohgyPr_oX56TwUZDa-qeepTzM4GhJ_k1mZeCgpS9oqA0MgPjaf5_rImkYDwdJycS_zXPXl7u79tOHYQ9U_P9JrVs-_Z1xfj8XMoSrqr65rCgLr1iElRGO78zbHzC8Pzw-HqI0KNwLh4fohasdGeOF9aK7ROuWbo8kUN096SDFyEpp1Y51Z2kIRzdmD-654fH0AmnpLeoHT6jZ-lyNBoFSYGiNEYdQ8v_Vw-WjZD63I1vjMrjEeMzJdqyFinjM8bnZNTBjPTvMCOqmnyvyvY6FNiFkdP_ivPMptWhFy-yU2ihtk6634QWNIdOK-DAtMtZfn0vmN6frIYwoDp_gAUyzNCj0GtNmCUBPTQITrQInfDNiLgqJfQGhv9IiWIv8ED2IbbHGULnwlNTeCE1uL5qdghkhzBe0bpg334XDYHz0XiU0LjTJopn6U2UH7GLsAgK1x56XTVCb-IUHQJPAyOtOfqV0josbNXAA8EK6ET1JjZhLwhdQ1iUpCWo2Jnzu_F4aktYsCxLfoF5QCijwwKIACpgqwmUW08wy4JC5_ZuFCTrBAbMCQUE3LS8uIkA4eJq_vXVODu_G8Gd3DR-SGYcDAvhF-5CVcp3PCEs-7uUX1zWBrQJ87Kz6PpWlGoLJVaidxiyUwqHxP7zyA2FRNS9VLWjLRkCGJfxRyNV4HtdAUvvgJP1Ifj3sfjWvVIhB7HgOtmhkjHiNAeXpi0JIq6ldR5cpyR5ekC5nahrqTfDtcXvArHPBo1yAx3a4VqiqvcFC4-irrH-RsghAwSPtvDRGIUhsBZF1UAYN0twhlzbxrq47Kno_YN8Q7WFGF_G59p4KKXDymO9w0M0dfJ8koZKT2aTMqN85JMyLKLYGl9ApeAlnI0pAnewtqYNybiYB1fR1gvhaRLlTfBB6IM0ujrck8cfjaRwVRV23kGvqRuxvnh8hIy5SihhXRw1Rims_DNiTbkmmjAtsgR6h-5r57yBtVQEzyL2doi120U-yhlS9e2TC9p87DLEsuRyKR9b41ptj4CeX5VpA8CM4PQiFDHax5j-4aVyowac2B7bQf44FBdUQjM-81Ai-VnD2tgDFQEvZQS5szrO0iE8oRJUG7EwOB_PxlMqjHN3Y3B3878S-oZ68pm65ndTY3zDkUfSgT2-_pyXSp29KWl6kt5BvUjrPM3FABfjWc6neZ7N-KBZ1Hme1LPxbI2YzydTUdaY5hMx5SVOsylOB3JBr5FxwsdjPs6SdFROxXo9xTnPqkTM5wmbJNgKqUa0pkbGbgbSuR4XPJ2MZ9lAiRKVC69izjV-QLgloDm9HdgFMQ3LfuPYJFHSeXcU46VX4Tl9Vv9segvL0I9Sw0-JJqePU-Xqy5kifDIWLmfCoLdq0XjfhQXDV4yvNtI3fTmqTHhr7Z5cZHdnzZ9YecZXwSlK9c7r9wX_TwAAAP__ovQHIg">