1 //===-- unittests/RISCVISAInfoTest.cpp ------------------------------------===// 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/TargetParser/RISCVISAInfo.h" 10 #include "llvm/ADT/StringMap.h" 11 #include "llvm/Testing/Support/Error.h" 12 #include "gtest/gtest.h" 13 14 using ::testing::ElementsAre; 15 16 using namespace llvm; 17 18 bool operator==(const RISCVISAUtils::ExtensionVersion &A, 19 const RISCVISAUtils::ExtensionVersion &B) { 20 return A.Major == B.Major && A.Minor == B.Minor; 21 } 22 23 TEST(ParseNormalizedArchString, RejectsInvalidChars) { 24 for (StringRef Input : 25 {"RV32", "rV64", "rv32i2P0", "rv64i2p0_A2p0", "rv32e2.0"}) { 26 EXPECT_EQ( 27 toString(RISCVISAInfo::parseNormalizedArchString(Input).takeError()), 28 "string may only contain [a-z0-9_]"); 29 } 30 } 31 32 TEST(ParseNormalizedArchString, RejectsInvalidBaseISA) { 33 for (StringRef Input : {"rv32", "rv64", "rv32j", "rv65i"}) { 34 EXPECT_EQ( 35 toString(RISCVISAInfo::parseNormalizedArchString(Input).takeError()), 36 "arch string must begin with valid base ISA"); 37 } 38 } 39 40 TEST(ParseNormalizedArchString, RejectsMalformedInputs) { 41 for (StringRef Input : {"rv64e2p", "rv32i", "rv64ip1"}) { 42 EXPECT_EQ( 43 toString(RISCVISAInfo::parseNormalizedArchString(Input).takeError()), 44 "extension lacks version in expected format"); 45 } 46 47 for (StringRef Input : {"rv64i2p0_", "rv32i2p0__a2p0"}) { 48 EXPECT_EQ( 49 toString(RISCVISAInfo::parseNormalizedArchString(Input).takeError()), 50 "extension name missing after separator '_'"); 51 } 52 } 53 54 TEST(ParseNormalizedArchString, RejectsOnlyVersion) { 55 for (StringRef Input : {"rv64i2p0_1p0", "rv32i2p0_1p0"}) { 56 EXPECT_EQ( 57 toString(RISCVISAInfo::parseNormalizedArchString(Input).takeError()), 58 "missing extension name"); 59 } 60 } 61 62 TEST(ParseNormalizedArchString, RejectsBadZ) { 63 for (StringRef Input : {"rv64i2p0_z1p0", "rv32i2p0_z2a1p0"}) { 64 EXPECT_EQ( 65 toString(RISCVISAInfo::parseNormalizedArchString(Input).takeError()), 66 "'z' must be followed by a letter"); 67 } 68 } 69 70 TEST(ParseNormalizedArchString, RejectsBadS) { 71 for (StringRef Input : {"rv64i2p0_s1p0", "rv32i2p0_s2a1p0"}) { 72 EXPECT_EQ( 73 toString(RISCVISAInfo::parseNormalizedArchString(Input).takeError()), 74 "'s' must be followed by a letter"); 75 } 76 } 77 78 TEST(ParseNormalizedArchString, RejectsBadX) { 79 for (StringRef Input : {"rv64i2p0_x1p0", "rv32i2p0_x2a1p0"}) { 80 EXPECT_EQ( 81 toString(RISCVISAInfo::parseNormalizedArchString(Input).takeError()), 82 "'x' must be followed by a letter"); 83 } 84 } 85 86 TEST(ParseNormalizedArchString, DuplicateExtension) { 87 for (StringRef Input : {"rv64i2p0_a2p0_a1p0"}) { 88 EXPECT_EQ( 89 toString(RISCVISAInfo::parseNormalizedArchString(Input).takeError()), 90 "duplicate extension 'a'"); 91 } 92 } 93 94 TEST(ParseNormalizedArchString, AcceptsValidBaseISAsAndSetsXLen) { 95 auto MaybeRV32I = RISCVISAInfo::parseNormalizedArchString("rv32i2p0"); 96 ASSERT_THAT_EXPECTED(MaybeRV32I, Succeeded()); 97 RISCVISAInfo &InfoRV32I = **MaybeRV32I; 98 EXPECT_EQ(InfoRV32I.getExtensions().size(), 1UL); 99 EXPECT_TRUE(InfoRV32I.getExtensions().at("i") == 100 (RISCVISAUtils::ExtensionVersion{2, 0})); 101 EXPECT_EQ(InfoRV32I.getXLen(), 32U); 102 103 auto MaybeRV32E = RISCVISAInfo::parseNormalizedArchString("rv32e2p0"); 104 ASSERT_THAT_EXPECTED(MaybeRV32E, Succeeded()); 105 RISCVISAInfo &InfoRV32E = **MaybeRV32E; 106 EXPECT_EQ(InfoRV32E.getExtensions().size(), 1UL); 107 EXPECT_TRUE(InfoRV32E.getExtensions().at("e") == 108 (RISCVISAUtils::ExtensionVersion{2, 0})); 109 EXPECT_EQ(InfoRV32E.getXLen(), 32U); 110 111 auto MaybeRV64I = RISCVISAInfo::parseNormalizedArchString("rv64i2p0"); 112 ASSERT_THAT_EXPECTED(MaybeRV64I, Succeeded()); 113 RISCVISAInfo &InfoRV64I = **MaybeRV64I; 114 EXPECT_EQ(InfoRV64I.getExtensions().size(), 1UL); 115 EXPECT_TRUE(InfoRV64I.getExtensions().at("i") == 116 (RISCVISAUtils::ExtensionVersion{2, 0})); 117 EXPECT_EQ(InfoRV64I.getXLen(), 64U); 118 119 auto MaybeRV64E = RISCVISAInfo::parseNormalizedArchString("rv64e2p0"); 120 ASSERT_THAT_EXPECTED(MaybeRV64E, Succeeded()); 121 RISCVISAInfo &InfoRV64E = **MaybeRV64E; 122 EXPECT_EQ(InfoRV64E.getExtensions().size(), 1UL); 123 EXPECT_TRUE(InfoRV64E.getExtensions().at("e") == 124 (RISCVISAUtils::ExtensionVersion{2, 0})); 125 EXPECT_EQ(InfoRV64E.getXLen(), 64U); 126 } 127 128 TEST(ParseNormalizedArchString, AcceptsArbitraryExtensionsAndVersions) { 129 auto MaybeISAInfo = RISCVISAInfo::parseNormalizedArchString( 130 "rv64i5p1_m3p2_zmadeup11p12_sfoo2p0_xbar3p0"); 131 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 132 RISCVISAInfo &Info = **MaybeISAInfo; 133 EXPECT_EQ(Info.getExtensions().size(), 5UL); 134 EXPECT_TRUE(Info.getExtensions().at("i") == 135 (RISCVISAUtils::ExtensionVersion{5, 1})); 136 EXPECT_TRUE(Info.getExtensions().at("m") == 137 (RISCVISAUtils::ExtensionVersion{3, 2})); 138 EXPECT_TRUE(Info.getExtensions().at("zmadeup") == 139 (RISCVISAUtils::ExtensionVersion{11, 12})); 140 EXPECT_TRUE(Info.getExtensions().at("sfoo") == 141 (RISCVISAUtils::ExtensionVersion{2, 0})); 142 EXPECT_TRUE(Info.getExtensions().at("xbar") == 143 (RISCVISAUtils::ExtensionVersion{3, 0})); 144 } 145 146 TEST(ParseNormalizedArchString, UpdatesFLenMinVLenMaxELen) { 147 auto MaybeISAInfo = RISCVISAInfo::parseNormalizedArchString( 148 "rv64i2p0_d2p0_zvl64b1p0_zve64d1p0"); 149 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 150 RISCVISAInfo &Info = **MaybeISAInfo; 151 EXPECT_EQ(Info.getXLen(), 64U); 152 EXPECT_EQ(Info.getFLen(), 64U); 153 EXPECT_EQ(Info.getMinVLen(), 64U); 154 EXPECT_EQ(Info.getMaxELen(), 64U); 155 EXPECT_EQ(Info.getMaxELenFp(), 64U); 156 } 157 158 TEST(ParseNormalizedArchString, AcceptsUnknownMultiletter) { 159 auto MaybeISAInfo = RISCVISAInfo::parseNormalizedArchString( 160 "rv64i2p0_f2p0_d2p0_zicsr2p0_ykk1p0"); 161 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 162 RISCVISAInfo &Info = **MaybeISAInfo; 163 EXPECT_EQ(Info.toString(), "rv64i2p0_f2p0_d2p0_zicsr2p0_ykk1p0"); 164 } 165 166 TEST(ParseArchString, RejectsInvalidChars) { 167 for (StringRef Input : {"RV32", "rV64", "rv32i2P0", "rv64i2p0_A2p0"}) { 168 EXPECT_EQ(toString(RISCVISAInfo::parseArchString(Input, true).takeError()), 169 "string may only contain [a-z0-9_]"); 170 } 171 } 172 173 TEST(ParseArchString, RejectsInvalidBaseISA) { 174 for (StringRef Input : {"rv32", "rv64", "rv65i"}) { 175 EXPECT_EQ(toString(RISCVISAInfo::parseArchString(Input, true).takeError()), 176 "string must begin with rv32{i,e,g}, rv64{i,e,g}, or a supported " 177 "profile name"); 178 } 179 180 for (StringRef Input : {"rv32j", "rv32_i"}) { 181 EXPECT_EQ(toString(RISCVISAInfo::parseArchString(Input, true).takeError()), 182 "first letter after 'rv32' should be 'e', 'i' or 'g'"); 183 } 184 185 EXPECT_EQ(toString(RISCVISAInfo::parseArchString("rv64k", true).takeError()), 186 "first letter after 'rv64' should be 'e', 'i' or 'g'"); 187 } 188 189 TEST(ParseArchString, RejectsUnsupportedBaseISA) { 190 for (StringRef Input : {"rv128i", "rv128g"}) { 191 EXPECT_EQ(toString(RISCVISAInfo::parseArchString(Input, true).takeError()), 192 "string must begin with rv32{i,e,g}, rv64{i,e,g}, or a supported " 193 "profile name"); 194 } 195 } 196 197 TEST(ParseArchString, AcceptsSupportedBaseISAsAndSetsXLenAndFLen) { 198 auto MaybeRV32I = RISCVISAInfo::parseArchString("rv32i", true); 199 ASSERT_THAT_EXPECTED(MaybeRV32I, Succeeded()); 200 RISCVISAInfo &InfoRV32I = **MaybeRV32I; 201 const auto &ExtsRV32I = InfoRV32I.getExtensions(); 202 EXPECT_EQ(ExtsRV32I.size(), 1UL); 203 EXPECT_TRUE(ExtsRV32I.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); 204 EXPECT_EQ(InfoRV32I.getXLen(), 32U); 205 EXPECT_EQ(InfoRV32I.getFLen(), 0U); 206 EXPECT_EQ(InfoRV32I.getMinVLen(), 0U); 207 EXPECT_EQ(InfoRV32I.getMaxELen(), 0U); 208 EXPECT_EQ(InfoRV32I.getMaxELenFp(), 0U); 209 210 auto MaybeRV32E = RISCVISAInfo::parseArchString("rv32e", true); 211 ASSERT_THAT_EXPECTED(MaybeRV32E, Succeeded()); 212 RISCVISAInfo &InfoRV32E = **MaybeRV32E; 213 const auto &ExtsRV32E = InfoRV32E.getExtensions(); 214 EXPECT_EQ(ExtsRV32E.size(), 1UL); 215 EXPECT_TRUE(ExtsRV32E.at("e") == (RISCVISAUtils::ExtensionVersion{2, 0})); 216 EXPECT_EQ(InfoRV32E.getXLen(), 32U); 217 EXPECT_EQ(InfoRV32E.getFLen(), 0U); 218 EXPECT_EQ(InfoRV32E.getMinVLen(), 0U); 219 EXPECT_EQ(InfoRV32E.getMaxELen(), 0U); 220 EXPECT_EQ(InfoRV32E.getMaxELenFp(), 0U); 221 222 auto MaybeRV32G = RISCVISAInfo::parseArchString("rv32g", true); 223 ASSERT_THAT_EXPECTED(MaybeRV32G, Succeeded()); 224 RISCVISAInfo &InfoRV32G = **MaybeRV32G; 225 const auto &ExtsRV32G = InfoRV32G.getExtensions(); 226 EXPECT_EQ(ExtsRV32G.size(), 7UL); 227 EXPECT_TRUE(ExtsRV32G.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); 228 EXPECT_TRUE(ExtsRV32G.at("m") == (RISCVISAUtils::ExtensionVersion{2, 0})); 229 EXPECT_TRUE(ExtsRV32G.at("a") == (RISCVISAUtils::ExtensionVersion{2, 1})); 230 EXPECT_TRUE(ExtsRV32G.at("f") == (RISCVISAUtils::ExtensionVersion{2, 2})); 231 EXPECT_TRUE(ExtsRV32G.at("d") == (RISCVISAUtils::ExtensionVersion{2, 2})); 232 EXPECT_TRUE(ExtsRV32G.at("zicsr") == (RISCVISAUtils::ExtensionVersion{2, 0})); 233 EXPECT_TRUE(ExtsRV32G.at("zifencei") == 234 (RISCVISAUtils::ExtensionVersion{2, 0})); 235 EXPECT_EQ(InfoRV32G.getXLen(), 32U); 236 EXPECT_EQ(InfoRV32G.getFLen(), 64U); 237 EXPECT_EQ(InfoRV32G.getMinVLen(), 0U); 238 EXPECT_EQ(InfoRV32G.getMaxELen(), 0U); 239 EXPECT_EQ(InfoRV32G.getMaxELenFp(), 0U); 240 241 auto MaybeRV64I = RISCVISAInfo::parseArchString("rv64i", true); 242 ASSERT_THAT_EXPECTED(MaybeRV64I, Succeeded()); 243 RISCVISAInfo &InfoRV64I = **MaybeRV64I; 244 const auto &ExtsRV64I = InfoRV64I.getExtensions(); 245 EXPECT_EQ(ExtsRV64I.size(), 1UL); 246 EXPECT_TRUE(ExtsRV64I.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); 247 EXPECT_EQ(InfoRV64I.getXLen(), 64U); 248 EXPECT_EQ(InfoRV64I.getFLen(), 0U); 249 EXPECT_EQ(InfoRV64I.getMinVLen(), 0U); 250 EXPECT_EQ(InfoRV64I.getMaxELen(), 0U); 251 EXPECT_EQ(InfoRV64I.getMaxELenFp(), 0U); 252 253 auto MaybeRV64E = RISCVISAInfo::parseArchString("rv64e", true); 254 ASSERT_THAT_EXPECTED(MaybeRV64E, Succeeded()); 255 RISCVISAInfo &InfoRV64E = **MaybeRV64E; 256 const auto &ExtsRV64E = InfoRV64E.getExtensions(); 257 EXPECT_EQ(ExtsRV64E.size(), 1UL); 258 EXPECT_TRUE(ExtsRV64E.at("e") == (RISCVISAUtils::ExtensionVersion{2, 0})); 259 EXPECT_EQ(InfoRV64E.getXLen(), 64U); 260 EXPECT_EQ(InfoRV64E.getFLen(), 0U); 261 EXPECT_EQ(InfoRV64E.getMinVLen(), 0U); 262 EXPECT_EQ(InfoRV64E.getMaxELen(), 0U); 263 EXPECT_EQ(InfoRV64E.getMaxELenFp(), 0U); 264 265 auto MaybeRV64G = RISCVISAInfo::parseArchString("rv64g", true); 266 ASSERT_THAT_EXPECTED(MaybeRV64G, Succeeded()); 267 RISCVISAInfo &InfoRV64G = **MaybeRV64G; 268 const auto &ExtsRV64G = InfoRV64G.getExtensions(); 269 EXPECT_EQ(ExtsRV64G.size(), 7UL); 270 EXPECT_TRUE(ExtsRV64G.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); 271 EXPECT_TRUE(ExtsRV64G.at("m") == (RISCVISAUtils::ExtensionVersion{2, 0})); 272 EXPECT_TRUE(ExtsRV64G.at("a") == (RISCVISAUtils::ExtensionVersion{2, 1})); 273 EXPECT_TRUE(ExtsRV64G.at("f") == (RISCVISAUtils::ExtensionVersion{2, 2})); 274 EXPECT_TRUE(ExtsRV64G.at("d") == (RISCVISAUtils::ExtensionVersion{2, 2})); 275 EXPECT_TRUE(ExtsRV64G.at("zicsr") == (RISCVISAUtils::ExtensionVersion{2, 0})); 276 EXPECT_TRUE(ExtsRV64G.at("zifencei") == 277 (RISCVISAUtils::ExtensionVersion{2, 0})); 278 EXPECT_EQ(InfoRV64G.getXLen(), 64U); 279 EXPECT_EQ(InfoRV64G.getFLen(), 64U); 280 EXPECT_EQ(InfoRV64G.getMinVLen(), 0U); 281 EXPECT_EQ(InfoRV64G.getMaxELen(), 0U); 282 EXPECT_EQ(InfoRV64G.getMaxELenFp(), 0U); 283 284 auto MaybeRV64GCV = RISCVISAInfo::parseArchString("rv64gcv", true); 285 ASSERT_THAT_EXPECTED(MaybeRV64GCV, Succeeded()); 286 RISCVISAInfo &InfoRV64GCV = **MaybeRV64GCV; 287 const auto &ExtsRV64GCV = InfoRV64GCV.getExtensions(); 288 EXPECT_EQ(ExtsRV64GCV.size(), 17UL); 289 EXPECT_TRUE(ExtsRV64GCV.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); 290 EXPECT_TRUE(ExtsRV64GCV.at("m") == (RISCVISAUtils::ExtensionVersion{2, 0})); 291 EXPECT_TRUE(ExtsRV64GCV.at("a") == (RISCVISAUtils::ExtensionVersion{2, 1})); 292 EXPECT_TRUE(ExtsRV64GCV.at("f") == (RISCVISAUtils::ExtensionVersion{2, 2})); 293 EXPECT_TRUE(ExtsRV64GCV.at("d") == (RISCVISAUtils::ExtensionVersion{2, 2})); 294 EXPECT_TRUE(ExtsRV64GCV.at("c") == (RISCVISAUtils::ExtensionVersion{2, 0})); 295 EXPECT_TRUE(ExtsRV64GCV.at("zicsr") == (RISCVISAUtils::ExtensionVersion{2, 0})); 296 EXPECT_TRUE(ExtsRV64GCV.at("zifencei") == 297 (RISCVISAUtils::ExtensionVersion{2, 0})); 298 EXPECT_TRUE(ExtsRV64GCV.at("v") == (RISCVISAUtils::ExtensionVersion{1, 0})); 299 EXPECT_TRUE(ExtsRV64GCV.at("zve32x") == (RISCVISAUtils::ExtensionVersion{1, 0})); 300 EXPECT_TRUE(ExtsRV64GCV.at("zve32f") == (RISCVISAUtils::ExtensionVersion{1, 0})); 301 EXPECT_TRUE(ExtsRV64GCV.at("zve64x") == (RISCVISAUtils::ExtensionVersion{1, 0})); 302 EXPECT_TRUE(ExtsRV64GCV.at("zve64f") == (RISCVISAUtils::ExtensionVersion{1, 0})); 303 EXPECT_TRUE(ExtsRV64GCV.at("zve64d") == (RISCVISAUtils::ExtensionVersion{1, 0})); 304 EXPECT_TRUE(ExtsRV64GCV.at("zvl32b") == (RISCVISAUtils::ExtensionVersion{1, 0})); 305 EXPECT_TRUE(ExtsRV64GCV.at("zvl64b") == (RISCVISAUtils::ExtensionVersion{1, 0})); 306 EXPECT_TRUE(ExtsRV64GCV.at("zvl128b") == (RISCVISAUtils::ExtensionVersion{1, 0})); 307 EXPECT_EQ(InfoRV64GCV.getXLen(), 64U); 308 EXPECT_EQ(InfoRV64GCV.getFLen(), 64U); 309 EXPECT_EQ(InfoRV64GCV.getMinVLen(), 128U); 310 EXPECT_EQ(InfoRV64GCV.getMaxELen(), 64U); 311 EXPECT_EQ(InfoRV64GCV.getMaxELenFp(), 64U); 312 } 313 314 TEST(ParseArchString, RejectsUnrecognizedExtensionNamesByDefault) { 315 EXPECT_EQ(toString(RISCVISAInfo::parseArchString("rv64ib", true).takeError()), 316 "unsupported standard user-level extension 'b'"); 317 EXPECT_EQ( 318 toString( 319 RISCVISAInfo::parseArchString("rv32i_zmadeup", true).takeError()), 320 "unsupported standard user-level extension 'zmadeup'"); 321 EXPECT_EQ( 322 toString( 323 RISCVISAInfo::parseArchString("rv64g_smadeup", true).takeError()), 324 "unsupported standard supervisor-level extension 'smadeup'"); 325 EXPECT_EQ( 326 toString( 327 RISCVISAInfo::parseArchString("rv64g_xmadeup", true).takeError()), 328 "unsupported non-standard user-level extension 'xmadeup'"); 329 EXPECT_EQ( 330 toString(RISCVISAInfo::parseArchString("rv64ib1p0", true).takeError()), 331 "unsupported standard user-level extension 'b'"); 332 EXPECT_EQ( 333 toString( 334 RISCVISAInfo::parseArchString("rv32i_zmadeup1p0", true).takeError()), 335 "unsupported standard user-level extension 'zmadeup'"); 336 EXPECT_EQ( 337 toString( 338 RISCVISAInfo::parseArchString("rv64g_smadeup1p0", true).takeError()), 339 "unsupported standard supervisor-level extension 'smadeup'"); 340 EXPECT_EQ( 341 toString( 342 RISCVISAInfo::parseArchString("rv64g_xmadeup1p0", true).takeError()), 343 "unsupported non-standard user-level extension 'xmadeup'"); 344 } 345 346 TEST(ParseArchString, IgnoresUnrecognizedExtensionNamesWithIgnoreUnknown) { 347 for (StringRef Input : {"rv32ib", "rv32i_zmadeup", 348 "rv64i_smadeup", "rv64i_xmadeup"}) { 349 auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true, false, true); 350 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 351 RISCVISAInfo &Info = **MaybeISAInfo; 352 const auto &Exts = Info.getExtensions(); 353 EXPECT_EQ(Exts.size(), 1UL); 354 EXPECT_TRUE(Exts.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); 355 } 356 357 // Checks that supported extensions aren't incorrectly ignored when a 358 // version is present (an early version of the patch had this mistake). 359 auto MaybeISAInfo = 360 RISCVISAInfo::parseArchString("rv32i_zbc1p0_xmadeup", true, false, true); 361 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 362 const auto &Exts = (*MaybeISAInfo)->getExtensions(); 363 EXPECT_TRUE(Exts.at("zbc") == (RISCVISAUtils::ExtensionVersion{1, 0})); 364 } 365 366 TEST(ParseArchString, AcceptsVersionInLongOrShortForm) { 367 for (StringRef Input : {"rv64i2p1"}) { 368 auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true); 369 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 370 const auto &Exts = (*MaybeISAInfo)->getExtensions(); 371 EXPECT_TRUE(Exts.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); 372 } 373 for (StringRef Input : {"rv32i_zfinx1", "rv32i_zfinx1p0"}) { 374 auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true); 375 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 376 const auto &Exts = (*MaybeISAInfo)->getExtensions(); 377 EXPECT_TRUE(Exts.at("zfinx") == (RISCVISAUtils::ExtensionVersion{1, 0})); 378 } 379 } 380 381 TEST(ParseArchString, RejectsUnrecognizedExtensionVersionsByDefault) { 382 EXPECT_EQ( 383 toString(RISCVISAInfo::parseArchString("rv64i2p", true).takeError()), 384 "minor version number missing after 'p' for extension 'i'"); 385 EXPECT_EQ( 386 toString(RISCVISAInfo::parseArchString("rv64i1p0", true).takeError()), 387 "unsupported version number 1.0 for extension 'i'"); 388 EXPECT_EQ( 389 toString(RISCVISAInfo::parseArchString("rv64i9p9", true).takeError()), 390 "unsupported version number 9.9 for extension 'i'"); 391 EXPECT_EQ( 392 toString(RISCVISAInfo::parseArchString("rv32im0p1", true).takeError()), 393 "unsupported version number 0.1 for extension 'm'"); 394 EXPECT_EQ(toString(RISCVISAInfo::parseArchString("rv32izifencei10p10", true) 395 .takeError()), 396 "unsupported version number 10.10 for extension 'zifencei'"); 397 } 398 399 TEST(ParseArchString, 400 UsesDefaultVersionForUnrecognisedBaseISAVersionWithIgnoreUnknown) { 401 for (StringRef Input : {"rv32i0p1", "rv32i99p99", "rv64i0p1", "rv64i99p99"}) { 402 auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true, false, true); 403 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 404 const auto &Exts = (*MaybeISAInfo)->getExtensions(); 405 EXPECT_EQ(Exts.size(), 1UL); 406 EXPECT_TRUE(Exts.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); 407 } 408 for (StringRef Input : {"rv32e0p1", "rv32e99p99", "rv64e0p1", "rv64e99p99"}) { 409 auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true, false, true); 410 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 411 const auto &Exts = (*MaybeISAInfo)->getExtensions(); 412 EXPECT_EQ(Exts.size(), 1UL); 413 EXPECT_TRUE(Exts.at("e") == (RISCVISAUtils::ExtensionVersion{2, 0})); 414 } 415 } 416 417 TEST(ParseArchString, 418 IgnoresExtensionsWithUnrecognizedVersionsWithIgnoreUnknown) { 419 for (StringRef Input : {"rv32im1p1", "rv64i_svnapot10p9", "rv32i_zicsr0p5"}) { 420 auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true, false, true); 421 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 422 const auto &Exts = (*MaybeISAInfo)->getExtensions(); 423 EXPECT_EQ(Exts.size(), 1UL); 424 EXPECT_TRUE(Exts.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); 425 } 426 } 427 428 TEST(ParseArchString, AcceptsUnderscoreSplittingExtensions) { 429 for (StringRef Input : {"rv32imafdczifencei", "rv32i_m_a_f_d_c_zifencei"}) { 430 auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true); 431 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 432 const auto &Exts = (*MaybeISAInfo)->getExtensions(); 433 EXPECT_EQ(Exts.size(), 8UL); 434 EXPECT_EQ(Exts.count("i"), 1U); 435 EXPECT_EQ(Exts.count("m"), 1U); 436 EXPECT_EQ(Exts.count("a"), 1U); 437 EXPECT_EQ(Exts.count("f"), 1U); 438 EXPECT_EQ(Exts.count("d"), 1U); 439 EXPECT_EQ(Exts.count("c"), 1U); 440 EXPECT_EQ(Exts.count("zicsr"), 1U); 441 EXPECT_EQ(Exts.count("zifencei"), 1U); 442 } 443 } 444 445 TEST(ParseArchString, AcceptsRelaxSingleLetterExtensions) { 446 for (StringRef Input : 447 {"rv32imfad", "rv32im_fa_d", "rv32im2p0fad", "rv32i2p1m2p0fad"}) { 448 auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true); 449 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 450 const auto &Exts = (*MaybeISAInfo)->getExtensions(); 451 EXPECT_EQ(Exts.size(), 6UL); 452 EXPECT_EQ(Exts.count("i"), 1U); 453 EXPECT_EQ(Exts.count("m"), 1U); 454 EXPECT_EQ(Exts.count("f"), 1U); 455 EXPECT_EQ(Exts.count("a"), 1U); 456 EXPECT_EQ(Exts.count("d"), 1U); 457 EXPECT_EQ(Exts.count("zicsr"), 1U); 458 } 459 } 460 461 TEST(ParseArchString, AcceptsRelaxMixedLetterExtensions) { 462 for (StringRef Input : 463 {"rv32i_zihintntl_m_a_f_d_svinval", "rv32izihintntl_mafdsvinval", 464 "rv32i_zihintntl_mafd_svinval"}) { 465 auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true); 466 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 467 const auto &Exts = (*MaybeISAInfo)->getExtensions(); 468 EXPECT_EQ(Exts.size(), 8UL); 469 EXPECT_EQ(Exts.count("i"), 1U); 470 EXPECT_EQ(Exts.count("m"), 1U); 471 EXPECT_EQ(Exts.count("a"), 1U); 472 EXPECT_EQ(Exts.count("f"), 1U); 473 EXPECT_EQ(Exts.count("d"), 1U); 474 EXPECT_EQ(Exts.count("zihintntl"), 1U); 475 EXPECT_EQ(Exts.count("svinval"), 1U); 476 EXPECT_EQ(Exts.count("zicsr"), 1U); 477 } 478 } 479 480 TEST(ParseArchString, AcceptsAmbiguousFromRelaxExtensions) { 481 for (StringRef Input : {"rv32i_zba_m", "rv32izba_m", "rv32izba1p0_m2p0"}) { 482 auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true); 483 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 484 const auto &Exts = (*MaybeISAInfo)->getExtensions(); 485 EXPECT_EQ(Exts.size(), 3UL); 486 EXPECT_EQ(Exts.count("i"), 1U); 487 EXPECT_EQ(Exts.count("zba"), 1U); 488 EXPECT_EQ(Exts.count("m"), 1U); 489 } 490 for (StringRef Input : 491 {"rv32ia_zba_m", "rv32iazba_m", "rv32ia2p1zba1p0_m2p0"}) { 492 auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true); 493 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 494 const auto &Exts = (*MaybeISAInfo)->getExtensions(); 495 EXPECT_EQ(Exts.size(), 4UL); 496 EXPECT_EQ(Exts.count("i"), 1U); 497 EXPECT_EQ(Exts.count("zba"), 1U); 498 EXPECT_EQ(Exts.count("m"), 1U); 499 EXPECT_EQ(Exts.count("a"), 1U); 500 } 501 } 502 503 TEST(ParseArchString, RejectsRelaxExtensionsNotStartWithEorIorG) { 504 EXPECT_EQ( 505 toString(RISCVISAInfo::parseArchString("rv32zba_im", true).takeError()), 506 "first letter after 'rv32' should be 'e', 'i' or 'g'"); 507 } 508 509 TEST(ParseArchString, 510 RejectsMultiLetterExtensionFollowBySingleLetterExtensions) { 511 for (StringRef Input : {"rv32izbam", "rv32i_zbam"}) 512 EXPECT_EQ(toString(RISCVISAInfo::parseArchString(Input, true).takeError()), 513 "unsupported standard user-level extension 'zbam'"); 514 EXPECT_EQ( 515 toString(RISCVISAInfo::parseArchString("rv32izbai_m", true).takeError()), 516 "unsupported standard user-level extension 'zbai'"); 517 EXPECT_EQ( 518 toString(RISCVISAInfo::parseArchString("rv32izbaim", true).takeError()), 519 "unsupported standard user-level extension 'zbaim'"); 520 EXPECT_EQ( 521 toString( 522 RISCVISAInfo::parseArchString("rv32i_zba1p0m", true).takeError()), 523 "unsupported standard user-level extension 'zba1p0m'"); 524 } 525 526 TEST(ParseArchString, RejectsDoubleOrTrailingUnderscore) { 527 EXPECT_EQ( 528 toString(RISCVISAInfo::parseArchString("rv64i__m", true).takeError()), 529 "extension name missing after separator '_'"); 530 531 for (StringRef Input : 532 {"rv32ezicsr__zifencei", "rv32i_", "rv32izicsr_", "rv64im_"}) { 533 EXPECT_EQ(toString(RISCVISAInfo::parseArchString(Input, true).takeError()), 534 "extension name missing after separator '_'"); 535 } 536 } 537 538 TEST(ParseArchString, RejectsDuplicateExtensionNames) { 539 EXPECT_EQ(toString(RISCVISAInfo::parseArchString("rv64ii", true).takeError()), 540 "invalid standard user-level extension 'i'"); 541 EXPECT_EQ(toString(RISCVISAInfo::parseArchString("rv32ee", true).takeError()), 542 "invalid standard user-level extension 'e'"); 543 EXPECT_EQ( 544 toString(RISCVISAInfo::parseArchString("rv64imm", true).takeError()), 545 "duplicated standard user-level extension 'm'"); 546 EXPECT_EQ( 547 toString( 548 RISCVISAInfo::parseArchString("rv32i_zicsr_zicsr", true).takeError()), 549 "duplicated standard user-level extension 'zicsr'"); 550 } 551 552 TEST(ParseArchString, 553 RejectsExperimentalExtensionsIfNotEnableExperimentalExtension) { 554 EXPECT_EQ( 555 toString(RISCVISAInfo::parseArchString("rv64iztso", false).takeError()), 556 "requires '-menable-experimental-extensions' for experimental extension " 557 "'ztso'"); 558 } 559 560 TEST(ParseArchString, 561 AcceptsExperimentalExtensionsIfEnableExperimentalExtension) { 562 // Note: If ztso becomes none-experimental, this test will need 563 // updating (and unfortunately, it will still pass). The failure of 564 // RejectsExperimentalExtensionsIfNotEnableExperimentalExtension will 565 // hopefully serve as a reminder to update. 566 auto MaybeISAInfo = RISCVISAInfo::parseArchString("rv64iztso", true, false); 567 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 568 const auto &Exts = (*MaybeISAInfo)->getExtensions(); 569 EXPECT_EQ(Exts.size(), 2UL); 570 EXPECT_EQ(Exts.count("ztso"), 1U); 571 auto MaybeISAInfo2 = RISCVISAInfo::parseArchString("rv64iztso0p1", true); 572 ASSERT_THAT_EXPECTED(MaybeISAInfo2, Succeeded()); 573 const auto &Exts2 = (*MaybeISAInfo2)->getExtensions(); 574 EXPECT_EQ(Exts2.size(), 2UL); 575 EXPECT_EQ(Exts2.count("ztso"), 1U); 576 } 577 578 TEST(ParseArchString, 579 RequiresExplicitVersionNumberForExperimentalExtensionByDefault) { 580 EXPECT_EQ( 581 toString(RISCVISAInfo::parseArchString("rv64iztso", true).takeError()), 582 "experimental extension requires explicit version number `ztso`"); 583 } 584 585 TEST(ParseArchString, 586 AcceptsUnrecognizedVersionIfNotExperimentalExtensionVersionCheck) { 587 auto MaybeISAInfo = 588 RISCVISAInfo::parseArchString("rv64iztso9p9", true, false); 589 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 590 const auto &Exts = (*MaybeISAInfo)->getExtensions(); 591 EXPECT_EQ(Exts.size(), 2UL); 592 EXPECT_TRUE(Exts.at("ztso") == (RISCVISAUtils::ExtensionVersion{9, 9})); 593 } 594 595 TEST(ParseArchString, RejectsUnrecognizedVersionForExperimentalExtension) { 596 EXPECT_EQ( 597 toString(RISCVISAInfo::parseArchString("rv64iztso9p9", true).takeError()), 598 "unsupported version number 9.9 for experimental extension 'ztso' " 599 "(this compiler supports 0.1)"); 600 } 601 602 TEST(ParseArchString, RejectsExtensionVersionForG) { 603 for (StringRef Input : {"rv32g1c", "rv64g2p0"}) { 604 EXPECT_EQ(toString(RISCVISAInfo::parseArchString(Input, true).takeError()), 605 "version not supported for 'g'"); 606 } 607 } 608 609 TEST(ParseArchString, AddsImpliedExtensions) { 610 // Does not attempt to exhaustively test all implications. 611 auto MaybeRV64ID = RISCVISAInfo::parseArchString("rv64id", true); 612 ASSERT_THAT_EXPECTED(MaybeRV64ID, Succeeded()); 613 const auto &ExtsRV64ID = (*MaybeRV64ID)->getExtensions(); 614 EXPECT_EQ(ExtsRV64ID.size(), 4UL); 615 EXPECT_EQ(ExtsRV64ID.count("i"), 1U); 616 EXPECT_EQ(ExtsRV64ID.count("f"), 1U); 617 EXPECT_EQ(ExtsRV64ID.count("d"), 1U); 618 EXPECT_EQ(ExtsRV64ID.count("zicsr"), 1U); 619 620 auto MaybeRV32IZKN = RISCVISAInfo::parseArchString("rv64izkn", true); 621 ASSERT_THAT_EXPECTED(MaybeRV32IZKN, Succeeded()); 622 const auto &ExtsRV32IZKN = (*MaybeRV32IZKN)->getExtensions(); 623 EXPECT_EQ(ExtsRV32IZKN.size(), 8UL); 624 EXPECT_EQ(ExtsRV32IZKN.count("i"), 1U); 625 EXPECT_EQ(ExtsRV32IZKN.count("zbkb"), 1U); 626 EXPECT_EQ(ExtsRV32IZKN.count("zbkc"), 1U); 627 EXPECT_EQ(ExtsRV32IZKN.count("zbkx"), 1U); 628 EXPECT_EQ(ExtsRV32IZKN.count("zkne"), 1U); 629 EXPECT_EQ(ExtsRV32IZKN.count("zknd"), 1U); 630 EXPECT_EQ(ExtsRV32IZKN.count("zknh"), 1U); 631 EXPECT_EQ(ExtsRV32IZKN.count("zkn"), 1U); 632 } 633 634 TEST(ParseArchString, RejectsConflictingExtensions) { 635 for (StringRef Input : {"rv32ifzfinx", "rv64gzdinx"}) { 636 EXPECT_EQ(toString(RISCVISAInfo::parseArchString(Input, true).takeError()), 637 "'f' and 'zfinx' extensions are incompatible"); 638 } 639 640 for (StringRef Input : {"rv32idc_zcmp1p0", "rv64idc_zcmp1p0"}) { 641 EXPECT_EQ(toString(RISCVISAInfo::parseArchString(Input, true).takeError()), 642 "'zcmp' extension is incompatible with 'c' extension when 'd' " 643 "extension is enabled"); 644 } 645 646 for (StringRef Input : {"rv32id_zcd1p0_zcmp1p0", "rv64id_zcd1p0_zcmp1p0"}) { 647 EXPECT_EQ(toString(RISCVISAInfo::parseArchString(Input, true).takeError()), 648 "'zcmp' extension is incompatible with 'zcd' extension when 'd' " 649 "extension is enabled"); 650 } 651 652 for (StringRef Input : {"rv32idc_zcmt1p0", "rv64idc_zcmt1p0"}) { 653 EXPECT_EQ(toString(RISCVISAInfo::parseArchString(Input, true).takeError()), 654 "'zcmt' extension is incompatible with 'c' extension when 'd' " 655 "extension is enabled"); 656 } 657 658 for (StringRef Input : {"rv32id_zcd1p0_zcmt1p0", "rv64id_zcd1p0_zcmt1p0"}) { 659 EXPECT_EQ(toString(RISCVISAInfo::parseArchString(Input, true).takeError()), 660 "'zcmt' extension is incompatible with 'zcd' extension when 'd' " 661 "extension is enabled"); 662 } 663 664 for (StringRef Input : {"rv64if_zcf"}) { 665 EXPECT_EQ(toString(RISCVISAInfo::parseArchString(Input, true).takeError()), 666 "'zcf' is only supported for 'rv32'"); 667 } 668 } 669 670 TEST(ToFeatures, IIsDroppedAndExperimentalExtensionsArePrefixed) { 671 auto MaybeISAInfo1 = 672 RISCVISAInfo::parseArchString("rv64im_ztso", true, false); 673 ASSERT_THAT_EXPECTED(MaybeISAInfo1, Succeeded()); 674 EXPECT_THAT((*MaybeISAInfo1)->toFeatures(), 675 ElementsAre("+m", "+experimental-ztso")); 676 677 auto MaybeISAInfo2 = 678 RISCVISAInfo::parseArchString("rv32e_ztso_xventanacondops", true, false); 679 ASSERT_THAT_EXPECTED(MaybeISAInfo2, Succeeded()); 680 EXPECT_THAT((*MaybeISAInfo2)->toFeatures(), 681 ElementsAre("+e", "+experimental-ztso", "+xventanacondops")); 682 } 683 684 TEST(ToFeatures, UnsupportedExtensionsAreDropped) { 685 auto MaybeISAInfo = 686 RISCVISAInfo::parseNormalizedArchString("rv64i2p0_m2p0_xmadeup1p0"); 687 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 688 EXPECT_THAT((*MaybeISAInfo)->toFeatures(), ElementsAre("+m")); 689 } 690 691 TEST(ToFeatures, UnsupportedExtensionsAreKeptIfIgnoreUnknownIsFalse) { 692 auto MaybeISAInfo = 693 RISCVISAInfo::parseNormalizedArchString("rv64i2p0_m2p0_xmadeup1p0"); 694 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 695 EXPECT_THAT((*MaybeISAInfo)->toFeatures(false, false), 696 ElementsAre("+m", "+xmadeup")); 697 } 698 699 TEST(ToFeatures, AddAllExtensionsAddsNegativeExtensions) { 700 auto MaybeISAInfo = RISCVISAInfo::parseNormalizedArchString("rv64i2p0_m2p0"); 701 ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); 702 703 auto Features = (*MaybeISAInfo)->toFeatures(true); 704 EXPECT_GT(Features.size(), 1UL); 705 EXPECT_EQ(Features.front(), "+m"); 706 // Every feature after should be a negative feature 707 for (auto &NegativeExt : llvm::drop_begin(Features)) 708 EXPECT_TRUE(NegativeExt.substr(0, 1) == "-"); 709 } 710 711 TEST(OrderedExtensionMap, ExtensionsAreCorrectlyOrdered) { 712 RISCVISAUtils::OrderedExtensionMap Exts; 713 for (auto ExtName : {"y", "l", "m", "c", "i", "xfoo", "xbar", "sfoo", "sbar", 714 "zmfoo", "zzfoo", "zfinx", "zicsr"}) 715 Exts[ExtName] = {1, 0}; 716 717 std::vector<std::string> ExtNames; 718 for (const auto &Ext : Exts) 719 ExtNames.push_back(Ext.first); 720 721 // FIXME: 'l' and 'y' should be ordered after 'i', 'm', 'c'. 722 EXPECT_THAT(ExtNames, 723 ElementsAre("i", "m", "l", "c", "y", "zicsr", "zmfoo", "zfinx", 724 "zzfoo", "sbar", "sfoo", "xbar", "xfoo")); 725 } 726 727 TEST(ParseArchString, ZceImplication) { 728 auto MaybeRV32IZce = RISCVISAInfo::parseArchString("rv32izce", true); 729 ASSERT_THAT_EXPECTED(MaybeRV32IZce, Succeeded()); 730 const auto &ExtsRV32IZce = (*MaybeRV32IZce)->getExtensions(); 731 EXPECT_EQ(ExtsRV32IZce.size(), 7UL); 732 EXPECT_EQ(ExtsRV32IZce.count("i"), 1U); 733 EXPECT_EQ(ExtsRV32IZce.count("zicsr"), 1U); 734 EXPECT_EQ(ExtsRV32IZce.count("zca"), 1U); 735 EXPECT_EQ(ExtsRV32IZce.count("zcb"), 1U); 736 EXPECT_EQ(ExtsRV32IZce.count("zce"), 1U); 737 EXPECT_EQ(ExtsRV32IZce.count("zcmp"), 1U); 738 EXPECT_EQ(ExtsRV32IZce.count("zcmt"), 1U); 739 740 auto MaybeRV32IFZce = RISCVISAInfo::parseArchString("rv32ifzce", true); 741 ASSERT_THAT_EXPECTED(MaybeRV32IFZce, Succeeded()); 742 const auto &ExtsRV32IFZce = (*MaybeRV32IFZce)->getExtensions(); 743 EXPECT_EQ(ExtsRV32IFZce.size(), 9UL); 744 EXPECT_EQ(ExtsRV32IFZce.count("i"), 1U); 745 EXPECT_EQ(ExtsRV32IFZce.count("zicsr"), 1U); 746 EXPECT_EQ(ExtsRV32IFZce.count("f"), 1U); 747 EXPECT_EQ(ExtsRV32IFZce.count("zca"), 1U); 748 EXPECT_EQ(ExtsRV32IFZce.count("zcb"), 1U); 749 EXPECT_EQ(ExtsRV32IFZce.count("zce"), 1U); 750 EXPECT_EQ(ExtsRV32IFZce.count("zcf"), 1U); 751 EXPECT_EQ(ExtsRV32IFZce.count("zcmp"), 1U); 752 EXPECT_EQ(ExtsRV32IFZce.count("zcmt"), 1U); 753 754 auto MaybeRV32IDZce = RISCVISAInfo::parseArchString("rv32idzce", true); 755 ASSERT_THAT_EXPECTED(MaybeRV32IDZce, Succeeded()); 756 const auto &ExtsRV32IDZce = (*MaybeRV32IDZce)->getExtensions(); 757 EXPECT_EQ(ExtsRV32IDZce.size(), 10UL); 758 EXPECT_EQ(ExtsRV32IDZce.count("i"), 1U); 759 EXPECT_EQ(ExtsRV32IDZce.count("zicsr"), 1U); 760 EXPECT_EQ(ExtsRV32IDZce.count("f"), 1U); 761 EXPECT_EQ(ExtsRV32IDZce.count("d"), 1U); 762 EXPECT_EQ(ExtsRV32IDZce.count("zca"), 1U); 763 EXPECT_EQ(ExtsRV32IDZce.count("zcb"), 1U); 764 EXPECT_EQ(ExtsRV32IDZce.count("zce"), 1U); 765 EXPECT_EQ(ExtsRV32IDZce.count("zcf"), 1U); 766 EXPECT_EQ(ExtsRV32IDZce.count("zcmp"), 1U); 767 EXPECT_EQ(ExtsRV32IDZce.count("zcmt"), 1U); 768 769 auto MaybeRV64IZce = RISCVISAInfo::parseArchString("rv64izce", true); 770 ASSERT_THAT_EXPECTED(MaybeRV64IZce, Succeeded()); 771 const auto &ExtsRV64IZce = (*MaybeRV64IZce)->getExtensions(); 772 EXPECT_EQ(ExtsRV64IZce.size(), 7UL); 773 EXPECT_EQ(ExtsRV64IZce.count("i"), 1U); 774 EXPECT_EQ(ExtsRV64IZce.count("zicsr"), 1U); 775 EXPECT_EQ(ExtsRV64IZce.count("zca"), 1U); 776 EXPECT_EQ(ExtsRV64IZce.count("zcb"), 1U); 777 EXPECT_EQ(ExtsRV64IZce.count("zce"), 1U); 778 EXPECT_EQ(ExtsRV64IZce.count("zcmp"), 1U); 779 EXPECT_EQ(ExtsRV64IZce.count("zcmt"), 1U); 780 781 auto MaybeRV64IFZce = RISCVISAInfo::parseArchString("rv64ifzce", true); 782 ASSERT_THAT_EXPECTED(MaybeRV64IFZce, Succeeded()); 783 const auto &ExtsRV64IFZce = (*MaybeRV64IFZce)->getExtensions(); 784 EXPECT_EQ(ExtsRV64IFZce.size(), 8UL); 785 EXPECT_EQ(ExtsRV64IFZce.count("i"), 1U); 786 EXPECT_EQ(ExtsRV64IFZce.count("zicsr"), 1U); 787 EXPECT_EQ(ExtsRV64IFZce.count("f"), 1U); 788 EXPECT_EQ(ExtsRV64IFZce.count("zca"), 1U); 789 EXPECT_EQ(ExtsRV64IFZce.count("zcb"), 1U); 790 EXPECT_EQ(ExtsRV64IFZce.count("zce"), 1U); 791 EXPECT_EQ(ExtsRV64IFZce.count("zcmp"), 1U); 792 EXPECT_EQ(ExtsRV64IFZce.count("zcmt"), 1U); 793 794 EXPECT_EQ(ExtsRV64IFZce.count("zca"), 1U); 795 EXPECT_EQ(ExtsRV64IFZce.count("zcb"), 1U); 796 EXPECT_EQ(ExtsRV64IFZce.count("zce"), 1U); 797 EXPECT_EQ(ExtsRV64IFZce.count("zcmp"), 1U); 798 EXPECT_EQ(ExtsRV64IFZce.count("zcmt"), 1U); 799 800 auto MaybeRV64IDZce = RISCVISAInfo::parseArchString("rv64idzce", true); 801 ASSERT_THAT_EXPECTED(MaybeRV64IDZce, Succeeded()); 802 const auto &ExtsRV64IDZce = (*MaybeRV64IDZce)->getExtensions(); 803 EXPECT_EQ(ExtsRV64IDZce.size(), 9UL); 804 EXPECT_EQ(ExtsRV64IDZce.count("i"), 1U); 805 EXPECT_EQ(ExtsRV64IDZce.count("zicsr"), 1U); 806 EXPECT_EQ(ExtsRV64IDZce.count("f"), 1U); 807 EXPECT_EQ(ExtsRV64IDZce.count("d"), 1U); 808 EXPECT_EQ(ExtsRV64IDZce.count("zca"), 1U); 809 EXPECT_EQ(ExtsRV64IDZce.count("zcb"), 1U); 810 EXPECT_EQ(ExtsRV64IDZce.count("zce"), 1U); 811 EXPECT_EQ(ExtsRV64IDZce.count("zcmp"), 1U); 812 EXPECT_EQ(ExtsRV64IDZce.count("zcmt"), 1U); 813 } 814 815 TEST(isSupportedExtensionWithVersion, AcceptsSingleExtensionWithVersion) { 816 EXPECT_TRUE(RISCVISAInfo::isSupportedExtensionWithVersion("zbb1p0")); 817 EXPECT_FALSE(RISCVISAInfo::isSupportedExtensionWithVersion("zbb")); 818 EXPECT_FALSE(RISCVISAInfo::isSupportedExtensionWithVersion("zfoo1p0")); 819 EXPECT_FALSE(RISCVISAInfo::isSupportedExtensionWithVersion("zfoo")); 820 EXPECT_FALSE(RISCVISAInfo::isSupportedExtensionWithVersion("")); 821 EXPECT_FALSE(RISCVISAInfo::isSupportedExtensionWithVersion("c2p0zbb1p0")); 822 } 823 824 TEST(getTargetFeatureForExtension, RetrieveTargetFeatureFromOneExt) { 825 EXPECT_EQ(RISCVISAInfo::getTargetFeatureForExtension("zbb"), "zbb"); 826 EXPECT_EQ(RISCVISAInfo::getTargetFeatureForExtension("ztso0p1"), 827 "experimental-ztso"); 828 EXPECT_EQ(RISCVISAInfo::getTargetFeatureForExtension("ztso"), 829 "experimental-ztso"); 830 EXPECT_EQ(RISCVISAInfo::getTargetFeatureForExtension("zihintntl1234p4321"), 831 ""); 832 EXPECT_EQ(RISCVISAInfo::getTargetFeatureForExtension("zfoo"), ""); 833 EXPECT_EQ(RISCVISAInfo::getTargetFeatureForExtension(""), ""); 834 EXPECT_EQ(RISCVISAInfo::getTargetFeatureForExtension("zbbzihintntl"), ""); 835 } 836 837 TEST(RiscvExtensionsHelp, CheckExtensions) { 838 // clang-format off 839 std::string ExpectedOutput = 840 R"(All available -march extensions for RISC-V 841 842 Name Version Description 843 i 2.1 This is a long dummy description 844 e 2.0 845 m 2.0 846 a 2.1 847 f 2.2 848 d 2.2 849 c 2.0 850 v 1.0 851 h 1.0 852 zic64b 1.0 853 zicbom 1.0 854 zicbop 1.0 855 zicboz 1.0 856 ziccamoa 1.0 857 ziccif 1.0 858 zicclsm 1.0 859 ziccrse 1.0 860 zicntr 2.0 861 zicond 1.0 862 zicsr 2.0 863 zifencei 2.0 864 zihintntl 1.0 865 zihintpause 2.0 866 zihpm 2.0 867 zimop 1.0 868 zmmul 1.0 869 za128rs 1.0 870 za64rs 1.0 871 zacas 1.0 872 zama16b 1.0 873 zawrs 1.0 874 zfa 1.0 875 zfh 1.0 876 zfhmin 1.0 877 zfinx 1.0 878 zdinx 1.0 879 zca 1.0 880 zcb 1.0 881 zcd 1.0 882 zce 1.0 883 zcf 1.0 884 zcmop 1.0 885 zcmp 1.0 886 zcmt 1.0 887 zba 1.0 888 zbb 1.0 889 zbc 1.0 890 zbkb 1.0 891 zbkc 1.0 892 zbkx 1.0 893 zbs 1.0 894 zk 1.0 895 zkn 1.0 896 zknd 1.0 897 zkne 1.0 898 zknh 1.0 899 zkr 1.0 900 zks 1.0 901 zksed 1.0 902 zksh 1.0 903 zkt 1.0 904 zvbb 1.0 905 zvbc 1.0 906 zve32f 1.0 907 zve32x 1.0 908 zve64d 1.0 909 zve64f 1.0 910 zve64x 1.0 911 zvfh 1.0 912 zvfhmin 1.0 913 zvkb 1.0 914 zvkg 1.0 915 zvkn 1.0 916 zvknc 1.0 917 zvkned 1.0 918 zvkng 1.0 919 zvknha 1.0 920 zvknhb 1.0 921 zvks 1.0 922 zvksc 1.0 923 zvksed 1.0 924 zvksg 1.0 925 zvksh 1.0 926 zvkt 1.0 927 zvl1024b 1.0 928 zvl128b 1.0 929 zvl16384b 1.0 930 zvl2048b 1.0 931 zvl256b 1.0 932 zvl32768b 1.0 933 zvl32b 1.0 934 zvl4096b 1.0 935 zvl512b 1.0 936 zvl64b 1.0 937 zvl65536b 1.0 938 zvl8192b 1.0 939 zhinx 1.0 940 zhinxmin 1.0 941 shcounterenw 1.0 942 shgatpa 1.0 943 shtvala 1.0 944 shvsatpa 1.0 945 shvstvala 1.0 946 shvstvecd 1.0 947 smaia 1.0 948 smepmp 1.0 949 smstateen 1.0 950 ssaia 1.0 951 ssccptr 1.0 952 sscofpmf 1.0 953 sscounterenw 1.0 954 ssstateen 1.0 955 ssstrict 1.0 956 sstc 1.0 957 sstvala 1.0 958 sstvecd 1.0 959 ssu64xl 1.0 960 svade 1.0 961 svadu 1.0 962 svbare 1.0 963 svinval 1.0 964 svnapot 1.0 965 svpbmt 1.0 966 xcvalu 1.0 967 xcvbi 1.0 968 xcvbitmanip 1.0 969 xcvelw 1.0 970 xcvmac 1.0 971 xcvmem 1.0 972 xcvsimd 1.0 973 xsfcease 1.0 974 xsfvcp 1.0 975 xsfvfnrclipxfqf 1.0 976 xsfvfwmaccqqq 1.0 977 xsfvqmaccdod 1.0 978 xsfvqmaccqoq 1.0 979 xsifivecdiscarddlone 1.0 980 xsifivecflushdlone 1.0 981 xtheadba 1.0 982 xtheadbb 1.0 983 xtheadbs 1.0 984 xtheadcmo 1.0 985 xtheadcondmov 1.0 986 xtheadfmemidx 1.0 987 xtheadmac 1.0 988 xtheadmemidx 1.0 989 xtheadmempair 1.0 990 xtheadsync 1.0 991 xtheadvdot 1.0 992 xventanacondops 1.0 993 994 Experimental extensions 995 zicfilp 0.4 This is a long dummy description 996 zicfiss 0.4 997 zaamo 0.2 998 zabha 1.0 999 zalasr 0.1 1000 zalrsc 0.2 1001 zfbfmin 1.0 1002 ztso 0.1 1003 zvfbfmin 1.0 1004 zvfbfwma 1.0 1005 smmpm 0.8 1006 smnpm 0.8 1007 ssnpm 0.8 1008 sspm 0.8 1009 ssqosid 1.0 1010 supm 0.8 1011 1012 Supported Profiles 1013 rva20s64 1014 rva20u64 1015 rva22s64 1016 rva22u64 1017 rva23s64 1018 rva23u64 1019 rvb23s64 1020 rvb23u64 1021 rvi20u32 1022 rvi20u64 1023 rvm23u32 1024 1025 Use -march to specify the target's extension. 1026 For example, clang -march=rv32i_v1p0)"; 1027 // clang-format on 1028 1029 StringMap<StringRef> DummyMap; 1030 DummyMap["i"] = "This is a long dummy description"; 1031 DummyMap["experimental-zicfilp"] = "This is a long dummy description"; 1032 1033 outs().flush(); 1034 testing::internal::CaptureStdout(); 1035 riscvExtensionsHelp(DummyMap); 1036 outs().flush(); 1037 1038 std::string CapturedOutput = testing::internal::GetCapturedStdout(); 1039 EXPECT_TRUE([](std::string &Captured, std::string &Expected) { 1040 return Captured.find(Expected) != std::string::npos; 1041 }(CapturedOutput, ExpectedOutput)); 1042 } 1043