1 //===-------- llvm/unittest/CodeGen/ScalableVectorMVTsTest.cpp ------------===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 10 #include "llvm/CodeGen/ValueTypes.h" 11 #include "llvm/IR/LLVMContext.h" 12 #include "llvm/Support/MachineValueType.h" 13 #include "gtest/gtest.h" 14 15 using namespace llvm; 16 17 namespace { 18 19 TEST(ScalableVectorMVTsTest, IntegerMVTs) { 20 for (auto VecTy : MVT::integer_scalable_vector_valuetypes()) { 21 ASSERT_TRUE(VecTy.isValid()); 22 ASSERT_TRUE(VecTy.isInteger()); 23 ASSERT_TRUE(VecTy.isVector()); 24 ASSERT_TRUE(VecTy.isScalableVector()); 25 ASSERT_TRUE(VecTy.getScalarType().isValid()); 26 27 ASSERT_FALSE(VecTy.isFloatingPoint()); 28 } 29 } 30 31 TEST(ScalableVectorMVTsTest, FloatMVTs) { 32 for (auto VecTy : MVT::fp_scalable_vector_valuetypes()) { 33 ASSERT_TRUE(VecTy.isValid()); 34 ASSERT_TRUE(VecTy.isFloatingPoint()); 35 ASSERT_TRUE(VecTy.isVector()); 36 ASSERT_TRUE(VecTy.isScalableVector()); 37 ASSERT_TRUE(VecTy.getScalarType().isValid()); 38 39 ASSERT_FALSE(VecTy.isInteger()); 40 } 41 } 42 43 TEST(ScalableVectorMVTsTest, HelperFuncs) { 44 LLVMContext Ctx; 45 46 // Create with scalable flag 47 EVT Vnx4i32 = EVT::getVectorVT(Ctx, MVT::i32, 4, /*Scalable=*/true); 48 ASSERT_TRUE(Vnx4i32.isScalableVector()); 49 50 // Create with separate MVT::ElementCount 51 auto EltCnt = MVT::ElementCount(2, true); 52 EVT Vnx2i32 = EVT::getVectorVT(Ctx, MVT::i32, EltCnt); 53 ASSERT_TRUE(Vnx2i32.isScalableVector()); 54 55 // Create with inline MVT::ElementCount 56 EVT Vnx2i64 = EVT::getVectorVT(Ctx, MVT::i64, {2, true}); 57 ASSERT_TRUE(Vnx2i64.isScalableVector()); 58 59 // Check that changing scalar types/element count works 60 EXPECT_EQ(Vnx2i32.widenIntegerVectorElementType(Ctx), Vnx2i64); 61 EXPECT_EQ(Vnx4i32.getHalfNumVectorElementsVT(Ctx), Vnx2i32); 62 63 // Check that overloaded '*' and '/' operators work 64 EXPECT_EQ(EVT::getVectorVT(Ctx, MVT::i64, EltCnt * 2), MVT::nxv4i64); 65 EXPECT_EQ(EVT::getVectorVT(Ctx, MVT::i64, EltCnt / 2), MVT::nxv1i64); 66 67 // Check that float->int conversion works 68 EVT Vnx2f64 = EVT::getVectorVT(Ctx, MVT::f64, {2, true}); 69 EXPECT_EQ(Vnx2f64.changeTypeToInteger(), Vnx2i64); 70 71 // Check fields inside MVT::ElementCount 72 EltCnt = Vnx4i32.getVectorElementCount(); 73 EXPECT_EQ(EltCnt.Min, 4U); 74 ASSERT_TRUE(EltCnt.Scalable); 75 76 // Check that fixed-length vector types aren't scalable. 77 EVT V8i32 = EVT::getVectorVT(Ctx, MVT::i32, 8); 78 ASSERT_FALSE(V8i32.isScalableVector()); 79 EVT V4f64 = EVT::getVectorVT(Ctx, MVT::f64, {4, false}); 80 ASSERT_FALSE(V4f64.isScalableVector()); 81 82 // Check that MVT::ElementCount works for fixed-length types. 83 EltCnt = V8i32.getVectorElementCount(); 84 EXPECT_EQ(EltCnt.Min, 8U); 85 ASSERT_FALSE(EltCnt.Scalable); 86 } 87 88 } 89