1//===------- VectorTypeUtils.cpp - Vector type utility functions ----------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#include "llvm/IR/VectorTypeUtils.h"
10#include "llvm/ADT/SmallVectorExtras.h"
11
12using namespace llvm;
13
14/// A helper for converting structs of scalar types to structs of vector types.
15/// Note: Only unpacked literal struct types are supported.
16Type *llvm::toVectorizedStructTy(StructType *StructTy, ElementCount EC) {
17 if (EC.isScalar())
18 return StructTy;
19 assert(isUnpackedStructLiteral(StructTy) &&
20 "expected unpacked struct literal");
21 assert(all_of(StructTy->elements(), VectorType::isValidElementType) &&
22 "expected all element types to be valid vector element types");
23 return StructType::get(
24 Context&: StructTy->getContext(),
25 Elements: map_to_vector(C: StructTy->elements(), F: [&](Type *ElTy) -> Type * {
26 return VectorType::get(ElementType: ElTy, EC);
27 }));
28}
29
30/// A helper for converting structs of vector types to structs of scalar types.
31/// Note: Only unpacked literal struct types are supported.
32Type *llvm::toScalarizedStructTy(StructType *StructTy) {
33 assert(isUnpackedStructLiteral(StructTy) &&
34 "expected unpacked struct literal");
35 return StructType::get(
36 Context&: StructTy->getContext(),
37 Elements: map_to_vector(C: StructTy->elements(), F: [](Type *ElTy) -> Type * {
38 return ElTy->getScalarType();
39 }));
40}
41
42/// Returns true if `StructTy` is an unpacked literal struct where all elements
43/// are vectors of matching element count. This does not include empty structs.
44bool llvm::isVectorizedStructTy(StructType *StructTy) {
45 if (!isUnpackedStructLiteral(StructTy))
46 return false;
47 auto ElemTys = StructTy->elements();
48 if (ElemTys.empty() || !ElemTys.front()->isVectorTy())
49 return false;
50 ElementCount VF = cast<VectorType>(Val: ElemTys.front())->getElementCount();
51 return all_of(Range&: ElemTys, P: [&](Type *Ty) {
52 return Ty->isVectorTy() && cast<VectorType>(Val: Ty)->getElementCount() == VF;
53 });
54}
55
56/// Returns true if `StructTy` is an unpacked literal struct where all elements
57/// are scalars that can be used as vector element types.
58bool llvm::canVectorizeStructTy(StructType *StructTy) {
59 auto ElemTys = StructTy->elements();
60 return !ElemTys.empty() && isUnpackedStructLiteral(StructTy) &&
61 all_of(Range&: ElemTys, P: VectorType::isValidElementType);
62}
63